Использование статической переменной для кэширования данных

Мы разрабатываем приложение .NET 3.5 Windows Forms, используя LINQ to SQL и MVP. У нас есть класс DataRepository для извлечения данных:

public class DbUserRepository : IUserRepository 
{
  private IList<UserName> _users;

  public IList<UserName> GetUserNames()
  {
    if (_users == null)
    {
      // retrieve _users from DB
    }

    return _users;
  }

Чтобы кэшировать список пользователей во всех экземплярах DBUserRepository, мы собирались использовать блок приложений кэширования корпоративной библиотеки.

Но это произошло со мной, не мог ли я сделать _users статическим членом? По какой-то причине это похоже на "старую школу", но это работает. Есть ли недостатки в этом? Это плохой дизайн?

private static IList<UserName> _users;

Спасибо

Ответ 1

Самая большая нижняя сторона этого делает именно то, что означает static; хотя у вас может быть много объектов DbUserRepository, они всегда будут иметь только одну переменную _users. Случаи, когда это вызывает проблемы:

  • Если ваше приложение когда-либо становится многопоточным, и вы хотите, чтобы в каждом потоке был свой собственный пользовательский репозиторий (независимо от того, зависит ли это от того, что репозиторий означает в контексте вашей системы)

  • Групповое тестирование класса DbUserRepository становится более сложным, потому что если вы выполняете несколько модульных тестов в этом классе, они будут переносить состояние вместе с ними из теста в тестовый, что означает, что тестовый запуск становится зависимым от порядка., что довольно нежелательно

Ответ 2

для простого кэширования. Я думаю, что статическая переменная прекрасна, просто нужно быть немного осторожным в использовании блокировок для защиты нескольких потоков, обращающихся к переменной _users. Однако лучшим подходом может быть использование класса кэша ASP.NET. Я знаю, что это в пространстве имен System.Web, но вы можете использовать его вне приложения ASP.NET.

Ответ 3

Несколько вещей, чтобы рассмотреть.

  • Поток Безопасность инициализации переменной
  • AppDomains. Статические переменные являются локальными для экземпляра AppDomain. Поэтому, если у вас запущено несколько приложений AppDomains, у вас будет несколько экземпляров кеша

Это может быть или не быть интересным для вашей заявки. Вероятно, нет, но стоит отметить.

Ответ 4

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