Thread
开启线程
thread.Start()开启线程
1、无参数情况
ThreadStart method = () =>
{
Thread.Sleep(3000);
this.DoSomethingLong("btnThread_Click");
};
Thread thread = new Thread(method);
thread.Start();
2、带参数情况
ParameterizedThreadStart mehtod = s =>
{
Console.WriteLine(s.ToString());
this.DoSomethingLong("btnThread_Click");
};
Thread thread1 = new Thread(mehtod);
thread1.Start("Hugh");
线程等待
线程等待的处理方式:
- thread.ThreadState获取线程的状态
- thread.Join()让线程等待
//可以通过判断状态来做到线程等待
//1.等待
while (thread.ThreadState!=ThreadState.Stopped)
{
Thread.Sleep(100);
}
//2.Join 等待
thread.Join();//主线程等待子线程计算完成;卡界面
thread.Join(2000);//等待2000ms,过时不候;
其他用法
- thread.Suspend();//挂起、暂停
- thread.Resume(); //恢复暂停的线程
- thread.Abort();//停止,对外抛出ThreadAbortException异常
- Thread.ResetAbort();//让停止的线程继续允许
- thread.Priority = ThreadPriority.Normal; //线程优先级,其实是提高优先执行的概率;有意外;优先执行并不代表优先结束; 千万不要用这个来控制线程的执行顺序;
- thread.IsBackground = true;//后台线程;进程关闭,线程也就消失了
- thread.IsBackground = false; //前台线程:进程关闭,线程执行完计算才消失
这些函数做不到线程的立刻暂定或者停止,有延时。
thread.Suspend();//挂起、暂停
thread.Resume(); //恢复暂停的线程
thread.Abort();//停止 对外抛出ThreadAbortException异常
Thread.ResetAbort();//让停止的线程继续允许
thread.Priority = ThreadPriority.Normal; //线程优先级,其实是提高优先执行的概率;有意外;优先执行并不代表优先结束; 千万不要用这个来控制线程的执行顺序;
thread.IsBackground = true;//后台线程;进程关闭,线程也就消失了
thread.IsBackground = false; //前台线程:进程关闭,线程执行完计算才消失
控制线程执行顺序–无返回值
如果想要控制线程顺序呢?回调;
- 1.本质是第一个线程里的动作执行完毕以后,去执行第二个动作;
- 2.既然是子线程来执行:必然是异步的,不能卡界面;
1、通过线程等待来控制顺序,但是会卡界面
/// <summary>
/// 控制线程顺序
/// //两个委托封装回调
/// </summary>
/// <param name="threadStart"></param>
/// <param name="actionCallBack"></param>
private void ThreadWithCallBack(ThreadStart threadStart, Action actionCallBack)
{
Thread thread = new Thread(threadStart);
thread.Start();
//1.While 死循环 判断状态 等待
{
while (thread.ThreadState != ThreadState.Stopped)
{
Thread.Sleep(100);
}
actionCallBack.Invoke();
}
//2.Join
//{
// thread.Join(); //卡界面
// actionCallBack.Invoke();
//}
}
调用方代码如下:
ThreadStart method = () =>
{
Console.WriteLine("欢迎大家。。");
Thread.Sleep(3000);
};
Action actionCallBack = () => {
Console.WriteLine("今晚不错");
};
this.ThreadWithCallBack(method, actionCallBack);
2、通过再包装一层线程来控制顺序,不会卡界面
/// <summary>
/// 控制线程顺序
/// //两个委托封装回调
/// </summary>
/// <param name="threadStart"></param>
/// <param name="actionCallBack"></param>
private void ThreadWithCallBack(ThreadStart threadStart, Action actionCallBack)
{
//将需要按顺序执行的方法再包装为一个线程
ThreadStart method = () =>
{
threadStart.Invoke();
actionCallBack.Invoke();
};
Thread thread = new Thread(method);
thread.Start();
}
控制线程执行顺序–有返回值
将返回值包装为一个Func委托
/// <summary>
/// 一个新的线程来执行委托里的动作
/// </summary>
/// <typeparam name="T"></typeparam>
/// <param name="func"></param>
/// <returns></returns>
private Func<T> ThreadWithReturen<T>(Func<T> func)
{
//花式玩法:返回一个委托
T t = default(T);
ThreadStart threadStart = () =>
{
t = func.Invoke();
};
Thread thread = new Thread(threadStart);
thread.Start();//不卡界面
return new Func<T>(() =>
{
thread.Join();
return t;
});
}
调用方代码如下:
Func<int> func = () =>
{
Thread.Sleep(3000);
return DateTime.Now.Year;
};
Func<int> func1Rusult = this.ThreadWithReturen<int>(func); //不卡界面
{
Console.WriteLine("");
Console.WriteLine("这里的执行也需要3秒钟。。。");
}
int iRsult = func1Rusult.Invoke(); //这里会卡界面,什么时候想要得到返回值的时候再去获取。