Если я обновию dataRow, я блокирую всю datatable или просто dataRow?
-
25-09-2019 - |
Вопрос
Предположим, я доступа к DataTable
из нескольких нитей. Если я хочу получить доступ к определенному ряду, я подозреваю, что мне нужно заблокировать эту операцию (я мог бы ошибиться об этом, но, по крайней мере, я знаю, что я в безопасности):
// this is a strongly-typed table
OrdersRow row = null;
lock (orderTable.Rows.SyncRoot) {
row = orderTable.FindByOrderId(myOrderId);
}
Но потом, если я хочу Обновить эта строка, я должен заблокировать стол (или, скорее, таблица Rows.SyncRoot
объект) опять таки, или я могу просто заблокировать ряд?
Решение
На самом деле, просто выполняя lock
В одном месте на DataTable или DataRow на самом деле не делать что-нибудь. Важный аспект, чтобы помнить в использовании Monitor
замки (что это то, что lock
Блок есть) - это то, что блокировка объекта ничего не делает; Это одна из причин, что некоторые защищают с использованием выделенных блокирующих объектов, а не блокируя сам ресурс, поскольку он заставляет вас реализовать, что вы должны выполнить блокировку (и на том же объекте), когда вы имеете дело с ресурсом.
Это сказано, это лучшая идея заблокировать весь DataTable
, как сам хранилище данных есть ( DataRow
объекты внутренне содержат только смещение в DataTable
Как откуда получить данные). Из-за этого, даже если вы синхронизируете доступ к отдельным строкам, обновляя два разные Строки одновременно приведут вам обновить те же механизм хранения данных в неинхронизированном способе.
Здесь есть конфликт между просмотром внутренних типов как «черный ящик» и блокировка только то, что вам нужно (что, в данном случае, приведет вас к неисправному заключению только блокировки строки) и пытаясь получить понимание внутренней работы типа и полагаться на детали реализации это мог изменить.
Upshot это то, что сейчас, вы должны заблокировать весь DataTable
Чтобы избежать обновления внутренних систем хранения данных в неинхронизированном виде.
Другие советы
Вам не нужно запирать для чтения - только для пишет / обновлений. Заблокируйте наименьшее количество, которую вы можете, чтобы обеспечить консистенцию данных ... Обычно только одна строка, которую вы обновляете. Если вы обновляете родительские / дочерние отношения между таблицами, вам нужно будет заблокировать каждую строку в каждой таблице.
DataTable безопасен только для многопоточных операций чтения:
http://msdn.microsoft.com/en-us/library/system.data.datatable.aspx.
http://social.msdn.microsoft.com/forums/en-us/netfxbcl/thrad/11b69e1a-ad6c-48d5-8e14-264Af5b0692e.
При чтении о DataTable есть противоречивая информация о возможности блокировки таблицы и позволяет безопасно обновлять данные в строке. Согласно второй ссылке, вы можете заблокировать таблицу и обновить строку. Быть этим от MS MVP, я бы сказал, что вы, вероятно, можете заблокировать стол и быть в порядке.