Windows Window и шаблон проектирования C # - PullRequest
1 голос
/ 18 сентября 2009

Я недавно перешел на устаревшую службу Windows, и она записывает следующее событие в системный журнал событий:

Код события: 7034
Описание: The Сервис MyService прекращен неожиданно. Он сделал это X время (с).

Я просматривал исходный код и нашел следующий шаблон кода в библиотеке классов обслуживания: (Это было упрощено для защиты невинных ..)

public static void StartService()
{
    //do some stuff...
    ManageCycle();
}

public static void ManageCycle()
{
   //do some stuff
   ManageCycle();
}

Как называется этот паттерн кодирования и может ли это вызвать остановку службы Windows (т.е. утечка памяти)?

Ответы [ 7 ]

3 голосов
/ 18 сентября 2009

Это похоже на шаблон исключения переполнения стека. Эран прав. Используйте цикл while:

public static void StartService()
{
    //do some stuff...
    isRunning = true;
    ManageCycle();
}

public static void ManageCycle()
{
   while(isRunning)
   {
   //do some stuff and wrap in exception handling
   }
}

public static void StopService()
{
    isRunning=false;
}
3 голосов
/ 18 сентября 2009

Предполагается, что выдается исключение StackOverflow (HA HA :)) из-за бесконечных рекурсивных вызовов.

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

1 голос
/ 18 сентября 2009

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

void ScanDirectory(Directory)
{
    // Handle Files
    if (currfile.directory)
        ScanDirectory(currfile)
}

Это имеет смысл, потому что это намного проще, чем делать это итеративно. Но в противном случае, когда вы просто повторяете действие снова и снова, делать его рекурсию совершенно не нужно, что приведет к неэффективности кода и в конечном итоге к переполнению стека.

1 голос
/ 18 сентября 2009

Это рекурсивный вызов, который в конечном итоге уничтожит стек.

0 голосов
/ 18 сентября 2009

Это рекурсивно, хорошо. Он будет постоянно вызывать себя (что плохо), что приведет к переполнению стека.

Что делает "// что-то"? Может быть, есть веская причина, по которой он сам себя называет, bНо без выхода из цикла (рекурсивно) приложение выйдет.

0 голосов
/ 18 сентября 2009

Рекурсия, кажется, что она рекурсивно вызывает себя. Я удивлен, что нет исключения переполнения стека. Возможно, свойство службы на машине, на которой выполняется это, настроено на перезапуск службы при сбое.

0 голосов
/ 18 сентября 2009

Это рекурсивный вызов без видимых критериев выхода. В конце концов он выйдет из стека, так как вызов ManageCycle никогда не возвращается.

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

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...