线程数大时不触发事件
Event is not triggered when number of threads is large
我在使用 C# 中的多线程和事件委托时遇到问题。如果有人能帮我解决这个问题,那就太好了。问题在于多个线程和事件。在单个线程或最多 10 个线程中,自定义事件被正确触发并且工作正常。但是,当我将线程数增加到 15 或 20 时,根本不会触发事件。这是一段代码示例:
LegacyMemberStream memberStream=new LegacyMemberStream();
memberStream.OpenStream();
legacyMemberStrm = (LegacyMemberStream)memberStream;
legacyMemberStrm.ThreadErrorOccur += OnParserThreadInterrupt;
这是 OnParserThreadInterrupt() 的代码:
private void OnParserThreadInterrupt(Object Sender, ThreadErrorEventArgs args)
{
// Exception logging is done here
}
并且,LegacyMemberStream.OpenStream() 方法的部分是:
parserThreads[i].OnThreadError = HandleThreadError;
parserThreads[i].StartThread();
该方法简单地初始化请求的线程数,并在发生异常时为每个线程分配事件,最后启动线程。
而且,LegacyMemberStream 中的 HandleThreadError 方法是:
public void HandleThreadError(Exception exception, string threadName)
{
lock (SyncObject)
{
Console.WriteLine("From parser thread");
for (int i = 0; i < parserThreads.Length; i++)
{
if (parserThreads[i].Name.Equals(threadName))
{
parserThreads[i].StopThread();
break;
}
}
int threadFailureErrorCode = -1111;
OnThreadFailure(new ThreadErrorEventArgs(threadFailureErrorCode, true,exception));
somethingQueue.StopQueuing();
}
}
LegacyMemberStream.OnThreadFailure:
protected virtual void OnThreadFailure(ThreadErrorEventArgs e)
{
lock (_locker)
{
var threaderrorOccur = ThreadErrorOccur;
// Console.WriteLine("Exception occurred");
if (threaderrorOccur != null)
{
ThreadErrorOccur(this, e);
}
}
}
对于任意数量的线程,从 OnThreadError 事件调用 HandleThreadError() 方法。
到目前为止,我从调试中发现,当线程数大于 15(或有时为 20)时,不会调用 OnParserThreadInterrupt() 方法。但是,对于相同的输入和相同的场景,当线程数较少时会触发 OnParserThreadInterrupt() 事件。我不明白为什么当线程数增加时没有触发事件。
根据您共享的这段代码,似乎唯一可能的原因是错误发生在您提交事件处理程序之前。所以只需将第一行的顺序更改为:
LegacyMemberStream memberStream=new LegacyMemberStream();
legacyMemberStrm = (LegacyMemberStream)memberStream;
legacyMemberStrm.ThreadErrorOccur += OnParserThreadInterrupt;
memberStream.OpenStream();
如果上下文切换发生在您有机会提交事件处理程序之前,那么此函数:
protected virtual void OnThreadFailure(ThreadErrorEventArgs e)
{
lock (_locker)
{
var threaderrorOccur = ThreadErrorOccur;
// Console.WriteLine("Exception occurred");
if (threaderrorOccur != null)
{
ThreadErrorOccur(this, e);
}
}
}
跳过了对 ThreadErrorOccur 的调用
因为 if 语句是假的。
为什么和线程数有关?我认为这是概率问题。也许创建许多线程会消耗足够的时间,所以主线程上下文切换,然后线程 运行(也在它们之间切换上下文),得到错误......所有这些都发生在主线程之前,whci 创建它们有有机会做订阅 ThreadErrorOccur 事件的行
希望它能解决您的问题。
我在使用 C# 中的多线程和事件委托时遇到问题。如果有人能帮我解决这个问题,那就太好了。问题在于多个线程和事件。在单个线程或最多 10 个线程中,自定义事件被正确触发并且工作正常。但是,当我将线程数增加到 15 或 20 时,根本不会触发事件。这是一段代码示例:
LegacyMemberStream memberStream=new LegacyMemberStream();
memberStream.OpenStream();
legacyMemberStrm = (LegacyMemberStream)memberStream;
legacyMemberStrm.ThreadErrorOccur += OnParserThreadInterrupt;
这是 OnParserThreadInterrupt() 的代码:
private void OnParserThreadInterrupt(Object Sender, ThreadErrorEventArgs args)
{
// Exception logging is done here
}
并且,LegacyMemberStream.OpenStream() 方法的部分是:
parserThreads[i].OnThreadError = HandleThreadError;
parserThreads[i].StartThread();
该方法简单地初始化请求的线程数,并在发生异常时为每个线程分配事件,最后启动线程。
而且,LegacyMemberStream 中的 HandleThreadError 方法是:
public void HandleThreadError(Exception exception, string threadName)
{
lock (SyncObject)
{
Console.WriteLine("From parser thread");
for (int i = 0; i < parserThreads.Length; i++)
{
if (parserThreads[i].Name.Equals(threadName))
{
parserThreads[i].StopThread();
break;
}
}
int threadFailureErrorCode = -1111;
OnThreadFailure(new ThreadErrorEventArgs(threadFailureErrorCode, true,exception));
somethingQueue.StopQueuing();
}
}
LegacyMemberStream.OnThreadFailure:
protected virtual void OnThreadFailure(ThreadErrorEventArgs e)
{
lock (_locker)
{
var threaderrorOccur = ThreadErrorOccur;
// Console.WriteLine("Exception occurred");
if (threaderrorOccur != null)
{
ThreadErrorOccur(this, e);
}
}
}
对于任意数量的线程,从 OnThreadError 事件调用 HandleThreadError() 方法。
到目前为止,我从调试中发现,当线程数大于 15(或有时为 20)时,不会调用 OnParserThreadInterrupt() 方法。但是,对于相同的输入和相同的场景,当线程数较少时会触发 OnParserThreadInterrupt() 事件。我不明白为什么当线程数增加时没有触发事件。
根据您共享的这段代码,似乎唯一可能的原因是错误发生在您提交事件处理程序之前。所以只需将第一行的顺序更改为:
LegacyMemberStream memberStream=new LegacyMemberStream();
legacyMemberStrm = (LegacyMemberStream)memberStream;
legacyMemberStrm.ThreadErrorOccur += OnParserThreadInterrupt;
memberStream.OpenStream();
如果上下文切换发生在您有机会提交事件处理程序之前,那么此函数:
protected virtual void OnThreadFailure(ThreadErrorEventArgs e)
{
lock (_locker)
{
var threaderrorOccur = ThreadErrorOccur;
// Console.WriteLine("Exception occurred");
if (threaderrorOccur != null)
{
ThreadErrorOccur(this, e);
}
}
}
跳过了对 ThreadErrorOccur 的调用 因为 if 语句是假的。
为什么和线程数有关?我认为这是概率问题。也许创建许多线程会消耗足够的时间,所以主线程上下文切换,然后线程 运行(也在它们之间切换上下文),得到错误......所有这些都发生在主线程之前,whci 创建它们有有机会做订阅 ThreadErrorOccur 事件的行 希望它能解决您的问题。