窗体中启动多线程t,执行方法method,方法中满足某个条件后,线程自己暂停;当用户点击按钮后,继续执行线程。注意是继续执行线程,不是另外启动线程。代码如下: public partial class Form1 : Form
{ Thread t;
public delegate void delegateM(int i);
delegateM dm; public Form1()
{
InitializeComponent();
} private void Form1_Load(object sender, EventArgs e)
{
dm = m;
t = new Thread(Method);
t.Start();
} void Method()
{
try
{
int i;
cnt: i = 0;
while (i < 300)
{
Thread.Sleep(10);
i++;
this.Invoke(dm, new object[] { i });//跨线程刷新窗体标题
Application.DoEvents();
}
Thread.Sleep(-1);//线程暂时停止
goto cnt;
}
catch
{ }
} void m(int i)
{
this.Text = i.ToString();
} private void button1_Click(object sender, EventArgs e)
{
try
{
t.Resume();//继续执行线程
}
catch
{ }
}
}调试发现,上述代码达不到预期目的。应该怎么修改呢?谢谢!
{ Thread t;
public delegate void delegateM(int i);
delegateM dm; public Form1()
{
InitializeComponent();
} private void Form1_Load(object sender, EventArgs e)
{
dm = m;
t = new Thread(Method);
t.Start();
} void Method()
{
try
{
int i;
cnt: i = 0;
while (i < 300)
{
Thread.Sleep(10);
i++;
this.Invoke(dm, new object[] { i });//跨线程刷新窗体标题
Application.DoEvents();
}
Thread.Sleep(-1);//线程暂时停止
goto cnt;
}
catch
{ }
} void m(int i)
{
this.Text = i.ToString();
} private void button1_Click(object sender, EventArgs e)
{
try
{
t.Resume();//继续执行线程
}
catch
{ }
}
}调试发现,上述代码达不到预期目的。应该怎么修改呢?谢谢!
private EventWaitHandle _EventWaitHandle;
_EventWaitHandle = new EventWaitHandle(false, EventResetMode.AutoReset);
_Thread = new Thread(Thread_Function);
private void Thread_Function()
{
DataBuf protocolData; protocolData = new DataBuf(_BufSize); while (true)
{
_EventWaitHandle.WaitOne();//在此处阻塞线程 try
{
while (!_DataReceiveCycle.IsEmpty())
{
// }
}
}
catch (Exception ex)
{
Prj.Log.Add(MethodResultHelper.BuildExceptionMsg(ex.Message));
}
}
}
_EventWaitHandle.Set(); //唤醒线程
你也可以用各种锁,AutoResetEvent,ManualResetEvent都可以啊
2. 所谓的等待,通常的做法就是轮空。
要把Thread的工作切碎,划分成细粒度的执行单元,如果标志为挂起的话,就是什么也不做
否则执行一个细粒度的工作
Suspend方法已经“过时”了,那么微软推荐什么方法呢?
{
public Form1()
{
InitializeComponent();
} private void Form1_Load(object sender, EventArgs e)
{
tmr.Elapsed += new System.Timers.ElapsedEventHandler(tmr_Elapsed);
tmr.Start();
} void tmr_Elapsed(object sender, System.Timers.ElapsedEventArgs e)
{
i++;
if (i >= 300)
i = 0;
this.BeginInvoke(new Action(() => { m(i); }));
} int i;
System.Timers.Timer tmr = new System.Timers.Timer(10); void m(int i)
{
this.Text = i.ToString();
} private void button1_Click(object sender, EventArgs e)
{
tmr.Enabled = !tmr.Enabled;
}
}
轮空的意思是,线程主动放弃他应得的时间片,直到他得到了足够的资源(或达到了某些条件)另外你那个DoEvents不是用在主线程上,没有任何意义 private void MainForm_Load(object sender, EventArgs e)
{
new Thread(method).Start();
}
private AutoResetEvent threadEvent = new AutoResetEvent(false);
private void button1_Click(object sender, EventArgs e)
{
threadEvent.Set();
}
void Method()
{
try
{
int i;
cnt: i = 0;
while (i < 300)
{
Thread.Sleep(10);
i++;
this.Invoke(dm, new object[] { i });//跨线程刷新窗体标题
}
threadEvent.WaitOne();
goto cnt;
}
catch
{ }
}
}
“另外你那个DoEvents不是用在主线程上,没有任何意义”,是吗?能具体说下吗?我理解DOEvents就是让其它线程处理消息,为什么只是用于主线程中呢?谢谢
线程重启的问题基本清楚了,应该就是你和3、4楼所说的,明天我再仔细看下MSDN的说法
private bool suspend = false;...
int i = 0;
while (i < 300)
{
if (!suspend)
{
i++;
this.Invoke(dm, new object[] { i });//跨线程刷新窗体标题
}
Thread.Sleep(100); //就算没有暂停也适当等待,否则窗体无响应,直接显示300
// Application.DoEvents(); 没用的语句
}
// 后面的goto也没啥用。当suspend=true时,while里就只执行Thread.Sleep
等都可以。
AutoResetEvent ev = new AutoResetEvent (false);
public void Do()
{
//do sth;
ev.waitone();//大小写自己调
// do sth;
}button-click()
{
ev.set();
}
{ Thread t;
public delegate void delegateM(int i);
delegateM dm; AutoResetEvent are; public Form1()
{
InitializeComponent();
} private void Form1_Load(object sender, EventArgs e)
{
are = new AutoResetEvent(false); dm = m;
t = new Thread(Method);
t.Start();
} void Method()
{
try
{
int i;
cnt: i = 0;
while (i < 300)
{
Thread.Sleep(10);
i++;
this.Invoke(dm, new object[] { i });//跨线程刷新窗体标题
Application.DoEvents();
}
are.WaitOne();//线程暂时停止
goto cnt;
}
catch
{ }
} void m(int i)
{
this.Text = i.ToString();
} private void button1_Click(object sender, EventArgs e)
{
try
{
are.Set();//继续执行线程
}
catch
{ }
}
}