мертвые блокировки nhibernate

Я думаю, что вопрос упускает суть архитектуры.NET - F#, C# и VB (и т.д.). все компилируются в IL, который тогда компилируется в машинный код с помощью JIT-компилятора. То, что программа была записана на функциональном языке, не релевантно - если существует оптимизация (как хвостовая рекурсия, и т.д.) доступна JIT-компилятору от IL, компилятор должен использовать в своих интересах его.

Естественно, это не означает, что запись функционального кода не важна - очевидно, существуют способы записать IL, который параллелизирует лучше - но многие из этих методов могли использоваться на любом языке.NET.

Так, нет никакой потребности отметить IL как прибывающий из F# для исследования его на потенциальный параллелизм, и при этом такая вещь не была бы желательна.

6
задан Chris 4 August 2009 в 20:21
поделиться

2 ответа

Такой дизайн может быть подвержен взаимоблокировке - обычно (не всегда) одно соединение вряд ли само зайдет в тупик, но несколько соединений, которые выполняют вставку и агрегирование для одной и той же таблицы, с большой вероятностью могут зайти в тупик. Это потому, что, хотя все действия в одной транзакции выглядят завершенными с точки зрения выполняющего работу соединения - база данных не блокирует транзакцию из «своих» записей - совокупные запросы из ДРУГИХ транзакций будут пытаться заблокировать вся таблица или большие ее части одновременно, и они могут оказаться в тупике.

Read Uncommitted - это не ваш друг в этом случае, потому что в основном говорится «игнорировать блокировки», что в какой-то момент будет означать нарушение правил, установленных вами для данных. IE подсчет записей в таблице будет неточным, и вы будете действовать в соответствии с этим неточным подсчетом. Ваш счет вернет 10 или 13, когда реальный ответ будет 11.

Лучший совет, который я могу дать, - перестроить логику вставки так, чтобы уловить идею счета, не считая буквально строк. Вы можете пойти в двух направлениях. У меня есть одна идея: буквально пронумеровать вставленные ваучеры с помощью последовательности и обеспечить ограничение самой последовательности.

  1. Создайте таблицу последовательности со столбцами (я предполагаю) MallID, nextVoucher, maxVouchers
  2. Залейте эту таблицу с помощью mallids, 1 и любое ограничение для каждого торгового центра
  3. Измените логику вставки на этот псевдокод:
Begin Transaction
Sanity check the nextVoucher for Mall in the sequence table; if too many exist abort
If less than MaxVouchers for Mall then {
  check, fetch, lock and increment nextVoucher
  if increment was successful then use the value of nextVoucher to perform your insert. 
    Include it in the target table.
}
Error? Rollback
No Error? Commit

Такая таблица последовательности в некоторой степени вредит параллелизму, но я думаю, что не столько, сколько подсчет строк в таблице постоянно. Обязательно выполните тест. Я буду действовать по этому неточному счету. Ваш счет вернет 10 или 13, когда реальный ответ будет 11.

Лучший совет, который я могу дать, - перестроить логику вставки так, чтобы уловить идею счета, не считая буквально строк. Вы можете пойти в двух направлениях. У меня есть такая идея: буквально пронумеровать вставленные ваучеры с помощью последовательности и установить ограничение для самой последовательности.

  1. Создайте таблицу последовательности со столбцами (я предполагаю) MallID, nextVoucher, maxVouchers
  2. Залейте эту таблицу с помощью mallids, 1 и любое ограничение для каждого торгового центра
  3. Измените логику вставки на этот псевдокод:
Begin Transaction
Sanity check the nextVoucher for Mall in the sequence table; if too many exist abort
If less than MaxVouchers for Mall then {
  check, fetch, lock and increment nextVoucher
  if increment was successful then use the value of nextVoucher to perform your insert. 
    Include it in the target table.
}
Error? Rollback
No Error? Commit

Такая таблица последовательности в некоторой степени вредит параллелизму, но я думаю, что не столько, сколько подсчет строк в таблице постоянно. Обязательно выполните тест. Я буду действовать по этому неточному счету. Ваш счет вернет 10 или 13, когда реальный ответ будет 11.

Лучший совет, который у меня есть, - перестроить логику вставки так, чтобы уловить идею счета, не считая буквально строк. Вы можете пойти в двух направлениях. У меня есть такая идея: буквально пронумеровать вставленные ваучеры с помощью последовательности и установить ограничение для самой последовательности.

  1. Создайте таблицу последовательности со столбцами (я предполагаю) MallID, nextVoucher, maxVouchers
  2. Залейте эту таблицу с помощью mallids, 1 и любое ограничение для каждого торгового центра
  3. Измените логику вставки на этот псевдокод:
Begin Transaction
Sanity check the nextVoucher for Mall in the sequence table; if too many exist abort
If less than MaxVouchers for Mall then {
  check, fetch, lock and increment nextVoucher
  if increment was successful then use the value of nextVoucher to perform your insert. 
    Include it in the target table.
}
Error? Rollback
No Error? Commit

Такая таблица последовательности в некоторой степени вредит параллелизму, но я думаю, что не столько, сколько подсчет строк в таблице постоянно. Обязательно выполните тест.

Лучший совет, который у меня есть, - перестроить логику вставки таким образом, чтобы улавливать идею подсчета, не считая буквально строк. Вы можете пойти в двух направлениях. У меня есть одна идея: буквально пронумеровать вставленные ваучеры с помощью последовательности и обеспечить ограничение самой последовательности.

  1. Создайте таблицу последовательности со столбцами (я предполагаю) MallID, nextVoucher, maxVouchers
  2. Залейте эту таблицу с помощью mallids, 1 и любое ограничение для каждого торгового центра
  3. Измените логику вставки на этот псевдокод:
Begin Transaction
Sanity check the nextVoucher for Mall in the sequence table; if too many exist abort
If less than MaxVouchers for Mall then {
  check, fetch, lock and increment nextVoucher
  if increment was successful then use the value of nextVoucher to perform your insert. 
    Include it in the target table.
}
Error? Rollback
No Error? Commit

Такая таблица последовательности в некоторой степени вредит параллелизму, но я думаю, что не столько, сколько подсчет строк в таблице постоянно. Обязательно выполните тест.

Лучший совет, который у меня есть, - перестроить логику вставки таким образом, чтобы улавливать идею подсчета, не считая буквально строк. Вы можете пойти в двух направлениях. У меня есть такая идея: буквально пронумеровать вставленные ваучеры с помощью последовательности и установить ограничение для самой последовательности.

  1. Создайте таблицу последовательности со столбцами (я предполагаю) MallID, nextVoucher, maxVouchers
  2. Залейте эту таблицу с помощью mallids, 1 и любое ограничение для каждого торгового центра
  3. Измените логику вставки на этот псевдокод:
Begin Transaction
Sanity check the nextVoucher for Mall in the sequence table; if too many exist abort
If less than MaxVouchers for Mall then {
  check, fetch, lock and increment nextVoucher
  if increment was successful then use the value of nextVoucher to perform your insert. 
    Include it in the target table.
}
Error? Rollback
No Error? Commit

Такая таблица последовательности в некоторой степени вредит параллелизму, но я думаю, что не столько, сколько подсчет строк в таблице постоянно. Обязательно выполните тест. У меня есть одна идея: буквально пронумеровать вставленные ваучеры с помощью последовательности и обеспечить ограничение самой последовательности.

  1. Создайте таблицу последовательности со столбцами (я предполагаю) MallID, nextVoucher, maxVouchers
  2. Залейте эту таблицу с помощью mallids, 1 и любое ограничение для каждого торгового центра
  3. Измените логику вставки на этот псевдокод:
Begin Transaction
Sanity check the nextVoucher for Mall in the sequence table; if too many exist abort
If less than MaxVouchers for Mall then {
  check, fetch, lock and increment nextVoucher
  if increment was successful then use the value of nextVoucher to perform your insert. 
    Include it in the target table.
}
Error? Rollback
No Error? Commit

Такая таблица последовательности в некоторой степени вредит параллелизму, но я думаю, что не столько, сколько подсчет строк в таблице постоянно. Обязательно выполните тест. У меня есть одна идея: буквально пронумеровать вставленные ваучеры с помощью последовательности и обеспечить ограничение самой последовательности.

  1. Создайте таблицу последовательности со столбцами (я предполагаю) MallID, nextVoucher, maxVouchers
  2. Залейте эту таблицу с помощью mallids, 1 и любое ограничение для каждого торгового центра
  3. Измените логику вставки на этот псевдокод:
Begin Transaction
Sanity check the nextVoucher for Mall in the sequence table; if too many exist abort
If less than MaxVouchers for Mall then {
  check, fetch, lock and increment nextVoucher
  if increment was successful then use the value of nextVoucher to perform your insert. 
    Include it in the target table.
}
Error? Rollback
No Error? Commit

Такая таблица последовательности в некоторой степени вредит параллелизму, но я думаю, что не столько, сколько подсчет строк в таблице постоянно. Обязательно выполните тест.

Begin Transaction
Sanity check the nextVoucher for Mall in the sequence table; if too many exist abort
If less than MaxVouchers for Mall then {
  check, fetch, lock and increment nextVoucher
  if increment was successful then use the value of nextVoucher to perform your insert. 
    Include it in the target table.
}
Error? Rollback
No Error? Commit

Такая таблица последовательности в некоторой степени вредит параллелизму, но я думаю, что не столько, сколько постоянный подсчет строк в таблице. Обязательно выполните тест.

Begin Transaction
Sanity check the nextVoucher for Mall in the sequence table; if too many exist abort
If less than MaxVouchers for Mall then {
  check, fetch, lock and increment nextVoucher
  if increment was successful then use the value of nextVoucher to perform your insert. 
    Include it in the target table.
}
Error? Rollback
No Error? Commit

Такая таблица последовательности в некоторой степени вредит параллелизму, но я думаю, что не столько, сколько постоянный подсчет строк в таблице. Обязательно выполните тест. Кроме того, важна [проверка, выборка, блокировка и приращение] - вы должны исключительно заблокировать строку в таблице последовательности, чтобы какое-либо другое соединение не использовало то же значение за доли секунды, прежде чем вы увеличите его. Я знаю синтаксис SQL для этого, но боюсь, что я не эксперт по nHibernate.

Для ошибок чтения незафиксированных данных проверьте это: http://sqlblog.com/blogs/merrill_aldrich/archive/2009 /07/29/transaction-isolation-dirty-reads-deadlocks-demo.aspx (отказ от ответственности: Merrill Aldrich - это я: -)

3
ответ дан 17 December 2019 в 18:18
поделиться

2 вопроса:

  1. Как часто удаляются ваучеры
  2. Любые возражения (сверх чистоты) против триггер уровня базы данных?
0
ответ дан 17 December 2019 в 18:18
поделиться
Другие вопросы по тегам:

Похожие вопросы: