Список <T>в кэше (операции безопасности) - PullRequest
0 голосов
/ 02 декабря 2010

Я занимаюсь разработкой веб-приложения с использованием asp.net mvc.

У меня есть список в кеше (список класса продукта моей модели). Итак, я делаю операции CRUD в этом кэшированном списке. Я знаю, что HttpContext.Current.Cache является typeSafe, но список нет. Я хотел бы знать, каков наилучший способ сделать мои операции потокобезопасными, чтобы избежать конфликтов?

Мой код выглядит примерно так:

public static class ProjectCached {
    const string key = "ProductList";
    // my cached list
    public static IList<Product> Products {
       get {
           if (HttpContext.Current.Cache[key] == null) {
              HttpContext.Current.Cache.Insert(key, /* get data from database */, ...);
           }
           return (List<Product>)HttpContext.Current.Cache[key];
       }
    }
    // my methods (operations on cached list)
    public static void Increase(long id) {
        var item = Products.FirstOrDefault(x => x.Id == id);
        if (item != null) {
          item.Prince += 1;
          item.LastUpdate = DateTime.Now;
        }       
    }

    public static void Remove(long id) {
        var item = Products.FirstOrDefault(x => x.Id == id);
        if (item != null) {
            Products.Remove(item);
        }       
    }
    // others methods 

}

У меня будет много пользователей, пишущих в этот список одновременно ...

Я знаю, что могу использовать ключевое слово "lock", но где мне это поставить? На моем объекте найден? в моем списке?

спасибо

Ответы [ 2 ]

1 голос
/ 02 декабря 2010

Рассмотрите возможность использования IDictionary вместо списка, например SortedList<TKey, TValue>
О безопасной нарезке резьбы: вы можете использовать

  1. lock ключевое слово

  2. ReaderWriterLockSlim - блокировка только при необходимости

  3. ConcurrentDictionary - если вам достаточно реализации, ориентированной на многопотоковое исполнение.

UPD: ReaderWriterLockSlim намного сложнее, чем простое ключевое слово lock. Использование ReaderWriterLockSlim позволяет многим читателям получать данные одновременно без блокировок. Но когда какой-то поток пытается записать данные, все остальные потоки будут заблокированы для чтения и записи.

0 голосов
/ 02 декабря 2010

Вы должны заблокировать его перед поиском предмета.

private Object syncObject = new Object();

public static void Increase(long id) {        
    lock(syncObject) {
        ...    
    }
}

public static void Remove(long id) {        
    lock(syncObject) {
        ...    
    }
}
...