我在C#Win应用程序中运行了2个辅助线程。
第一个线程读取Sql Server配置文件消息,并将其作为字符串添加到列表框中以形成一种队列。 另一个线程将逐个发送这些跟踪消息,并相应地从列表中删除它们。
现在我非常确定它会引起问题。任何方法可以确保只有一个线程能够访问这两个函数之一:
void AddItemThreadSafe(string item)
{
this.Invoke((MethodInvoker)delegate
{
listBoxCollection.Items.Add(item);
});
}
void RemoveItemThreadSafe()
{
this.Invoke((MethodInvoker)delegate
{
listBoxCollection.Items.RemoveAt(0);
});
}
答案 0 :(得分:3)
通常,使用lock
来同步对代码段的线程访问。
private static object listLocker = new object();
void AddItemThreadSafe(string item)
{
this.Invoke((MethodInvoker)delegate
{
lock (listLocker)
{
listBoxCollection.Items.Add(item);
}
});
}
void RemoveItemThreadSafe()
{
this.Invoke((MethodInvoker)delegate
{
lock (listLocker)
{
listBoxCollection.Items.RemoveAt(0);
}
});
}
在这种特殊情况下(如果我错了,有人纠正我),我相信你从同一个对象调用方法的事实已经同步了访问权限,使得锁多余。
答案 1 :(得分:2)
好消息是表单上的Invoke
方法已经为您同步了。这就是Invoke
的重点:对方法/委托进行排队,使其在创建表单的唯一UI线程上运行。
答案 2 :(得分:1)
使用内置Thread-Safe Collections 比如ConcurrentBag Class
从你的qustion Isaw你需要某种队列,所以使用ConcurrentQueue Class