我想知道这种方法是否有可能陷入僵局。
示例代码:单击应用程序按钮时,会创建一个Job对象并将其添加到作业列表中。添加代码受“锁定”保护。然后在计时器刻度事件中,我想从列表中删除已完成的作业 - 在计时器事件中锁定列表。
所以问题是,如果用户按下Add Job按钮,当timer事件锁定正在使用时,这个app会死锁吗?
Timer是一个Windows窗体计时器。
public partial class Form1 : Form
{
object listLock = new object();
List<Job> jobsList = new List<Job>();
public Form1()
{
InitializeComponent();
timer1.Start();
}
private void timer1_Tick(object sender, EventArgs e)
{
Job aJob;
lock(listLock)
{
for (int i = jobsList.Count - 1; i > -1; i--)
{
aJob = jobsList[i];
if (aJob.IsCompleted)
{
jobsList.RemoveAt(i);
}
}
}
}
private void button1_Click(object sender, EventArgs e)
{
lock (listLock)
{
Job aJob = new Job();
jobsList.Add(aJob);
}
}
}
//=====================================
class Job
{
bool isCompleted = false;
public bool IsCompleted
{
get { return isCompleted; }
set { isCompleted = value; }
}
public Job()
{
// do some work then mark complete
IsCompleted = true;
}
}
答案 0 :(得分:2)
从主消息循环调度定时器事件(来自Windows窗体定时器)。因此,它们永远不会与任何其他UI事件的处理程序重叠。
按下按钮将进入消息队列,并在定时器Tick处理程序完成后进行处理。 (因此,您不需要锁定仅由UI事件处理程序操纵的数据结构,因为它们将按照排队的顺序依次运行)