Chr☆s Kwok 的技术笔记

.NET, C#, WPF, WCF, WF, .NetCore & LINQ ... I know how it works because I know why it works ...

博客园 首页 新随笔 订阅 管理
 1 /*
 2 该实例是一个线程中lock用法的经典实例,使得到的balance不会为负数
 3 同时初始化十个线程,启动十个,但由于加锁,能够启动调用WithDraw方法的可能只能是其中几个
 4 作者:http://hi.baidu.com/jiang_yy_jiang
 5 */
 6 using System;
 7 
 8 namespace ThreadTest29
 9 {
10     class Account
11     {
12         private Object thisLock = new object();
13         int balance;
14         Random r = new Random();
15 
16         public Account(int initial)
17         {
18             balance = initial;
19         }
20 
21         int WithDraw(int amount)
22         {
23             if (balance < 0)
24             {
25                 throw new Exception("负的Balance.");
26             }
27             //确保只有一个线程使用资源,一个进入临界状态,使用对象互斥锁,10个启动了的线程不能全部执行该方法
28             lock (thisLock)
29             {
30                 if (balance >= amount)
31                 {
32                     Console.WriteLine("----------------------------:" + System.Threading.Thread.CurrentThread.Name + "---------------");
33                     
34                     Console.WriteLine("调用Withdrawal之前的Balance:" + balance);
35                     Console.WriteLine("把Amount输入 Withdrawal     :-" + amount);
36                     //如果没有加对象互斥锁,则可能10个线程都执行下面的减法,加减法所耗时间片段非常小,可能多个线程同时执行,出现负数。
37                     balance = balance - amount;
38                     Console.WriteLine("调用Withdrawal之后的Balance :" + balance);
39                     return amount;
40                 }
41                 else
42                 {
43                     //最终结果
44                     return 0;
45                 }
46             }
47         }
48         public void DoTransactions()
49         {
50             for (int i = 0; i < 100; i++)
51             {
52                 //生成balance的被减数amount的随机数
53                 WithDraw(r.Next(1, 100));
54             }
55         }
56     }
57 
58     class Test
59     {
60         static void Main(string[] args)
61         {
62             //初始化10个线程
63             System.Threading.Thread[] threads = new System.Threading.Thread[10];
64             //把balance初始化设定为1000
65             Account acc = new Account(1000);
66             for (int i = 0; i < 10; i++)
67             {
68                 System.Threading.Thread t = new System.Threading.Thread(new System.Threading.ThreadStart(acc.DoTransactions));
69                 threads[i] = t;
70                 threads[i].Name = "Thread" + i.ToString();
71             }
72             for (int i = 0; i < 10; i++)
73             {
74                 threads[i].Start();
75             }
76             Console.ReadKey();
77         }
78     }
79 }

 

posted on 2017-11-08 15:49  Chr☆s  阅读(890)  评论(0编辑  收藏  举报