Исходный код вики ConcurrentDictionary
Версия 9.2 от Alexandr Fokin на 2020/06/14 12:16
Последние авторы
author | version | line-number | content |
---|---|---|---|
1 | |||
2 | Пример работы ConcurrentDictionary AddOrUpdate: | ||
3 | В dictionary есть одной значение по ключу key1 - val1. | ||
4 | |||
5 | 1 Поток th1 запускает Update делегат по ключу key1. (Фиксирует текущее значение th1_v) | ||
6 | 2 Поток th2 запускает Update делегат по ключу key1. (Фиксирует текущее значение th2_v) | ||
7 | 3 Поток th2 заканчивает выполнение делегата Update. th1 сравнивает val1 = th2_v (Через equils). | ||
8 | Значение равны и th2 сохраняет результат. | ||
9 | 4 Поток th1 заканчивает выполнение делегата Update. th2 сравнивает val1 = th1_v (Через equils). | ||
10 | Значение НЕ равны и th2 повторно вызывает Update делегат. | ||
11 | (Если элемент был удален, то запустить делегат Add) | ||
12 | !Повторного вызова делегата не произойдет, в случает если результат работы th2 эквивалентен исходному начальному знаечнию val1. | ||
13 | |||
14 | Получается, что ни вызов AddOrUpdate, ни вызов конкретного делегата (Add/Update) сам по себе не блокирует значение в коллекции и не препятствует в изменении другим потокам. | ||
15 | |||
16 | По сути мы получаем **оптимистичную блокировку**. В случае неудачи которой, повторно вызывается действие обработки. Критерием сравнения блокировки является Equils. В таком случае возможно имеет смысл перегрузка Equils и наличии в сущности некоторого ключевого поля. Нечто вроде Change Version TimeStamp. | ||
17 | |||
18 | |||
19 | Ссылки: | ||
20 | [[Базы данных/Транзакции и блокировки>>https://wiki.denhome.ru/bin/view/Разработка/Базы%20данных/Транзакции%20и%20блокировки/]] |