[英]Multithreading code on button click event leaves the application in a hung state
這是我的代碼:
using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Linq;
using System.Text;
using System.Windows.Forms;
namespace MteWindowsForm
{
public partial class Form1 : Form
{
public Form1()
{
InitializeComponent();
dgv.AutoGenerateColumns = false;
AddCols();
AddRows();
}
void AddRows()
{
dgv.Rows.Add(10000);
bool istrue = true;
for (int i = 0; i < 10; i++)
{
for (int j = 0; j < 10000; j++)
{
if (istrue)
{
dgv.Rows[j].Cells[i].Value = "SomeText";
istrue = !istrue;
}
else istrue = !istrue;
}
}
}
void AddCols()
{
for (int i = 0; i < 10; i++)
{
DataGridViewColumn dgvCol = new DataGridViewTextBoxColumn();
string strText = "Column_" + i;
dgvCol.Name = strText;
dgvCol.HeaderText = strText;
dgvCol.FillWeight = 1;
dgv.Columns.Add(dgvCol);
}
}
private void button1_Click(object sender, EventArgs e)
{
//lock empty cells
}
}
}
這是我的表格:
但是,在單擊Button1
,應用程序將保持Button1
,並且不執行任何操作。 我的算法很簡單-我將datagridview列的計數從0->n/2
和n/2+1->n
划分,並鎖定一堆列並解鎖其余列。
請幫忙。
注釋中提到了潛在的死鎖,雖然我不確定是否是這種情況,但應用程序的掛起是由以下幾行引起的
t1.Join();
t2.Join();
Join
告訴UI線程應該阻塞直到這些線程完成。 您可能需要一個單獨的回調/事件來在線程完成時觸發,或者,如果您使用的是.NET 4.5,則可以使用任務異步功能並在后台線程調用中使用await
。
查看有關如何使用新的async / await關鍵字的示例 。
是的,您的應用程序出現了死鎖 。 您的工作線程在dgv.Invoke
等待。 dgv.Invoke
主線程完成,與此同時,您的主線程在Join
等待工人無限期完成,從而導致死鎖。
您在不必要的地方使用Thread
。 我的意思是您的LockCols
方法完全可以處理UI
因此您必須在UI中運行它。 通過在其他線程中運行循環,您將不會獲得任何好處。 以下代碼是您的更好的版本。
void LockCols(int istart, int iend, bool isReadOnly)
{
for (int idx = istart; idx < iend; idx++)
{
if (isReadOnly)
{
dgv.Columns[idx].ReadOnly = isReadOnly;
dgv.Columns[idx].HeaderText = dgv.Columns[idx].Name + "_" + "ReadOnly";
}
else
{
dgv.Columns[idx].ReadOnly = isReadOnly;
dgv.Columns[idx].HeaderText = dgv.Columns[idx].Name + "_" + "Not_ReadOnly";
}
}
}
private void button1_Click(object sender, EventArgs e)
{
System.Diagnostics.Stopwatch sw = new System.Diagnostics.Stopwatch();
sw.Start();
LockCols(0, dgv.Columns.Count / 2, true);
LockCols(dgv.Columns.Count / 2 + 1, dgv.Columns.Count, false);
sw.Stop();
MessageBox.Show(sw.Elapsed.ToString());
}
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.