多线程:
首先呢,聊下我对多线程的理解.
在我看来,多线程就相当于分身术,就像火影忍者的分身术,你可以有很多分身来帮你做各种事情.
进程=你的本体
线程=分身
由你的本体创造出来很多分身
你可以让他们做各种事情。
比如想象一下 你要看 一本书,100页,那你分身100个 然后一人分一页给他们看。 那是不是提升了100倍速度。
还有 做饭 比如 你要做几个菜:清蒸石斑,油闷大虾...等等
那你就可以分身 几个人 让他们 分别去做某一道菜 这样也大大缩减了做菜的时间
但是如果灶只有一个呢,那么分身在处理食材的时候 只能谁处理完快,谁到需要用灶哪一步 谁先用,另外一些 就只能等待灶 空闲下来才能继续。
那么在程序里面是怎么解决的呢 Lock 代码块锁 先判断 是否灶已被占用,没被用 就占用 用完后然后释放掉给其他人
示例:
object 灶 = new object();//创建一个锅 public void 做饭() { new Thread(() =>//做清蒸石斑的分身(线程) { //清洗 //杀鱼 //.. lock (灶)//开始用灶 { //大火 //小火 //直到菜好 } }).Start(); new Thread(() =>//做油闷大虾分身(线程) { //清洗 //去须 //.. lock (灶)//开始用灶 { //放油 //爆炒 //好吃了 } }).Start(); } //【时钟线程类别】 //这一类型的有定时执行的效果,并且多数是占用主进程的资源 //【Thread】 //using System.Threading;命名空间下的 //我平时最喜欢用的类 //灵活,多变,简单 /// <summary> /// 线程方法 /// </summary> /// <param name="obj"></param> public void TheradMethod(object obj) { //创建一个线程 Thread th = new Thread(() => { //匿名委托 里面写线程 执行的操作 }); th.Start(); } public void StartTh() { Thread th = new Thread(Method);//把方法委托给线程执行 th.Start(); } public void Method() { }
【Task】
System.Threading.Tasks
是线程池,由微软控制 封装了 如何分配 每个线程如何去执行 经测试是这样的:
下面 是 用Task跟Thread的区别
代码如下:
//Task 线程 private void button1_Click(object sender, EventArgs e) { int Ti = 0; int endTi = 0; System.Diagnostics.Stopwatch endsw = new System.Diagnostics.Stopwatch(); endsw.Start(); for (int i = 0; i < 10; i++) { new Task(() => { Ti++; System.Diagnostics.Stopwatch sw = new System.Diagnostics.Stopwatch(); sw.Start(); int n = Ti; add(this.label2); sw.Stop(); TimeSpan ts2 = sw.Elapsed; listBox1.Invoke(new Action(() => { listBox1.Items.Add($"Task {n} { sw.Elapsed}"); })); endTi++; if (endTi == 10) { endsw.Stop(); listBox1.Invoke(new Action(() => { listBox1.Items.Add($"Task END { endsw.Elapsed}"); })); } }).Start(); } } //Thread 线程 private void button2_Click(object sender, EventArgs e) { int thi = 0, endthi = 0; System.Diagnostics.Stopwatch endsw = new System.Diagnostics.Stopwatch(); endsw.Start(); for (int i = 0; i < 10; i++) { //委托写法 new Thread(() => { thi++; int n = thi; System.Diagnostics.Stopwatch sw = new System.Diagnostics.Stopwatch(); sw.Start(); add(this.label1); sw.Stop(); listBox1.Invoke(new Action(() => { listBox1.Items.Add($"Thread {n} { sw.Elapsed}"); })); endthi++; if (endthi == 10) { endsw.Stop(); listBox1.Invoke(new Action(() => { listBox1.Items.Add($"Thread END { endsw.Elapsed}"); })); } }).Start(); } } System.Object locker = new System.Object(); public void add(Control control) { // Access thread-sensitive resources. int i = 0; //Thread.Sleep(5000); while (i < 10000000)//运算的级别 { //if (Interlocked.Exchange(ref intbool,1)==0)//多线程共享原子操作 保证完整性 为多个线程共享的变量提供原子操作 //{ //Thread.Sleep(10);//测试表明 如果多个线程同时刷新界面 那界面的响应也是具有 一定数量级的响应速度,如果超过了 就会卡住 lock (locker) { intbool = 1; i++; //control.Invoke(new Action(() => //{ // control.Text = i.ToString(); //})); // Interlocked.Exchange(ref intbool, 0); } } }
运行结果如下:
while (i < 10000000)//运算的级别
while (i < 100000000)//运算的级别 上一个运算结果的10倍
你会发现 他们总花费的时间是差不多的,
Task 是线程池来控制的
我猜
Thread 是并行 由 CPU 时间片时序来控制
并且他们都是 多核运算的。
TaskCUP图
Thread CPU图
未完待续