Сведения о вопросе

None

15:23, 25th August, 2020

Теги

c#   .net   multithreading   exception    

A ThreadStateException возникает при попытке перезапустить поток

Просмотров: 438   Ответов: 3

Время от времени я получаю System.Threading.ThreadStateException при попытке перезапустить поток. Рассматриваемый код выглядит следующим образом:

// Make sure the thread is done stopping
while (this.mThread.ThreadState == ThreadState.Running)
{ 
    Thread.Sleep(0);
}
// Respawn a thread if the current one is stopped or doesn't exist
if (this.mThread == null || this.mThread.ThreadState == ThreadState.Stopped)
{ 
    this.mThread = new Thread(new ParameterizedThreadStart(Monitor)); }
// Start the thread
if (check)
{ 
    this.mThread.Start(60000); 
}
else
{   
    this.mThread.Start(0); 
}

Итак, два вопроса - Является ли это правильным способом делать вещи, и есть ли способ предотвратить возникновение ошибки?



  Сведения об ответе

KOMP

19:38, 4th August, 2020

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

if((mThread.ThreadState & ThreadState.Running) != 0)

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

mThread.Join();
mThread = new Thread(new ParameterizedThreadStart(Monitor));
if(check)
    mThread.Start(60000);
else
    mThread.Start(0);

Хотя если вы опишете проблему, которую пытаетесь решить, более подробно, я почти уверен, что будет лучшее решение. Ожидание окончания потока, чтобы просто перезапустить его снова, не кажется мне таким уж эффективным. Может быть, вам просто нужно какое-то межпотоковое общение?

Джон.


  Сведения об ответе

DINO

04:22, 5th August, 2020

Проблема заключается в том, что у вас есть код, который сначала проверяет, должен ли он создать новый объект потока, и еще один фрагмент кода, который определяет, следует ли запускать объект потока. Из-за условий гонки и тому подобных вещей ваш код может в конечном итоге попытаться вызвать .Start для существующего объекта потока. Учитывая, что вы не публикуете детали за переменной check , невозможно знать, что может вызвать такое поведение.

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

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


  Сведения об ответе

прога

23:31, 20th August, 2020

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

Есть потенциально пара вещей, которые могут произойти. Во-первых, поток, возможно, перешел от выполнения к StopRequested, который еще не полностью остановлен, поэтому ваша логика не создает новый поток, и вы пытаетесь запустить поток, который только что закончил работу или вот-вот завершится (ни то, ни другое не является допустимым состоянием для перезапуска).

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

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

if (this.mThread == null || this.mThread.ThreadState != ThreadState.Suspended)


Ответить на вопрос

Чтобы ответить на вопрос вам нужно войти в систему или зарегистрироваться