Для чего нужны статические переменные класса С# в ASP.NET?

Я знаю, что делают переменные статического класса в классе С++, но мне не очень понятен жизненный цикл переменных статического класса в классе С#, используемом для веб-приложения ASP.NET. Вот пример кода:

namespace MyWebApp
{
    public static class MyFunctions
    {
        private static string _cachedID;

        public static string getID(string strValue)
        {
            if(_cachedID == null)
                _cachedID = strValue;

            return _cachedID;
        }
    }
}

Может ли кто-нибудь объяснить это на простом английском языке для меня?


person ahmd0    schedule 02.07.2012    source источник


Ответы (3)


Я где-то читал.

Статическая переменная/поле возникает до выполнения статического конструктора для содержащего ее типа и прекращает свое существование, когда соответствующий домен приложения перестает существовать.

person kv-prajapati    schedule 02.07.2012
comment
Спасибо. Итак, скажем, если мое веб-приложение размещено по URL-адресу www.mydomain.com и первый пользователь входит в него через веб-браузер. Переменная cachedID будет установлена. Но тогда, если совершенно другой пользователь с другого компьютера войдет в систему по тому же URL-адресу, для cachedID уже будет установлено это первое значение. Это то, что вы говорите? - person ahmd0; 02.07.2012
comment
@ahmd0, да. Существует ровно один экземпляр статического члена для всего AppDomain. - person Alexei Levenkov; 02.07.2012
comment
@AlexeiLevenkov, есть разница между шаблоном singleton (в котором только один экземпляр может быть назначен статическому полю на время жизни AppDomain) и статическим полем в целом, в котором вы можете назначить столько экземпляров, сколько хотите во время время жизни AppDomain. - person Darin Dimitrov; 02.07.2012
comment
@DarinDimitrov, хммм ... Я не совсем уверен, как можно сформулировать тот факт, что статическое поле выделяет ровно единицы и используется во всем AppDomain. Моя попытка была экземпляром статического члена, который, как я теперь вижу, вместо этого может быть прочитан как ссылка на шаблон singleton. - person Alexei Levenkov; 02.07.2012
comment
static field allocated exactly ones and shared in whole AppDomain -› вот так идеально. Путаницы больше нет. - person Darin Dimitrov; 02.07.2012

Поскольку вы задаете этот вопрос в контексте многопоточного приложения ASP.NET, вам следует быть предельно осторожным. Проверьте следующий сценарий:

2 пользователя Боб и Алиса вызывают метод getID одновременно, передавая разные аргументы. Боб проходит Foo, а Алиса проходит Bar. Поскольку это первый вызов, переменная _cachedID еще не инициализирована, поэтому оба переходят в состояние if, Боб с небольшой задержкой. Итак, Алиса устанавливает статическую переменную the _cachedID в Bar, а через микросекунду Bob устанавливает для нее значение Foo. Теперь код продолжается, и функция возвращает Foo для обоих пользователей. Боб, конечно, счастлив, потому что он этого хотел, но Алиса хотела Bar.

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

Мораль этого заключается в том, что вы должны быть чрезвычайно осторожны при работе с общими/статическими данными в приложении ASP.NET. Если вам нужно его использовать, вам нужно правильно синхронизировать доступ к нему, иначе могут произойти очень плохие вещи. И они обычно происходят в рабочей среде, когда к вашему приложению одновременно обращаются несколько пользователей. На вашем локальном ПК все будет работать нормально.

И вернемся к вашему первоначальному вопросу о времени жизни статических полей: оно связано со временем жизни домена приложения.

person Darin Dimitrov    schedule 02.07.2012
comment
Спасибо, Дарин. Это объясняет это довольно хорошо. Я буду иметь это в виду. Однако есть один вопрос: как сервер IIS запоминает эту переменную, когда мы говорим о веб-браузерах, обращающихся к моему веб-приложению? - person ahmd0; 02.07.2012
comment
IIS ничего не помнит. Это домен приложения, в котором выполняется ваше приложение ASP.NET, которое хранит его в памяти. - person Darin Dimitrov; 02.07.2012

Классы, из которых вы не можете и не должны создавать объект, но вы можете получить к нему доступ только из статического контекста.

вы бы использовали свой пример следующим образом:

MyFunctions.getID("bla");

http://msdn.microsoft.com/en-us/library/79b3xss3(v=vs.80).aspx

person thommie    schedule 02.07.2012
comment
Спасибо за ссылку. Что мне не ясно, так это жизненный цикл этих статических переменных в среде ASP.NET? - person ahmd0; 02.07.2012