1.lock关键字 (多线程存在干涉,同时对一个共有参数进行修改时要用)
在多个线程之间共享数据时,需要考虑线程同步问题,必须确保每次只有一个线程访问和改变共享数据。
C#中使用lock语句可以轻松地设置和解除锁定以期达到每次只有一个线程访问和改变共享数据的目的。
例子:
class Program { static int pocket = 0; static int money = 1000; static int count = 10; static void Main(string[] args) { Thread[] thread = new Thread[count]; for (int i = 0; i < count; i++) { thread[i] = new Thread(new ParameterizedThreadStart(Fun)); } for (int i = 0; i < count; i++) { thread[i].Start(i); thread[i].Join(); } Console.Read(); } private static object lock_ = new object(); public static void Fun(object i) { lock (lock_) { Thread.Sleep(20); if (money >= 0) { money -= 100; pocket += 100; } Console.WriteLine("第" + i + "次" + "money=" + money + "pocket=" + pocket); } } }
运行结果:
2 线程的join方法
示例:
using System; using System.Threading; namespace Test { class TestThread { private static void FirstThreadFun() { for (int i = 0; i < 10; i++) { Console.WriteLine(Thread.CurrentThread.Name + " i = " + i); } Console.WriteLine(Thread.CurrentThread.Name + " 执行完毕"); } static void Main(string[] args) { //程序调用了Main()函数时,就起动了一个进程,同时也启动了一个线程[这个线程就是主线程]. Thread.CurrentThread.Name = "MainThread"; //创建第一个线程 Thread firstThread = new Thread(new ThreadStart(TestThread.FirstThreadFun)); //取名为 firstThread firstThread.Name = "firstThread"; for (int z = 0; z < 20; z++) { if (z == 10) { firstThread.Start(); firstThread.Join(); } else { Console.WriteLine(Thread.CurrentThread.Name + " z = " + z); } } Console.Read(); } } }
运行结果:
总结:
1.任何程序在执行时,至少有一个主线程。
2.firstThread.Start()启动了一个线程后,用firstThread.Join()这个方法加入一个线程[即:暂停了主线程的运行],那么操作系统就会马上执行这个新加入的线程
3.Join 就是加入的意思,也就是说新创建的线程加入到进程中,并马上执行
4.如果只是 firstThread.Start(),把 firstThread.Join()方法注释掉会是什么结果?
下面的图是运行结果:
从运行结果可以看出:
1.如果只是 firstThread.Start(),注释掉 firstThread.Join()这个方法后,主线程并不会暂停[也就是说,firstThread 线程并不会马上执行]
2.所以要想一个线程在启动后就马上执行,必须调用 Thread.Join()方法.
3.到这里,Thread.Join()这个方法的作用也就明显了:当调用了 Thread.Join()方法后,当前线程会立即被执行,其他所有的线程会被暂停执行.
当这个线程执行完后,其他线程才会继续执行.
我们通过其中提供的Thread类来创建和控制线程,ThreadPool类用于管理线程池等。
(此外还提供解决了线程执行安排,死锁,线程间通讯等实际问题的机制。)
Thread类有几个至关重要的方法,描述如下:
Start():启动线程;
Sleep(int):静态方法,暂停当前线程指定的毫秒数;
Abort():通常使用该方法来终止一个线程;
Suspend():该方法并不终止未完成的线程,它仅仅挂起线程,以后还可恢复;
Resume():恢复被Suspend()方法挂起的线程的执行;