多线程之进阶Lock替换掉synchronized--模拟多窗口共同卖票

学习到Lock对象啦,用它替换掉synchronized之前两个小例子。
效果差不多的,不过他有Condition特有的功能,这里没有体现出来。主要看替换点,结合前面synchronized写法,很好理解。

package com.cc.sellticket3;

import java.util.concurrent.locks.ReentrantLock;
/*
 * 卖票服务
 */
public class TicketService {
	private ReentrantLock lock = new ReentrantLock();
	
	private int tickets = 50;

	public TicketService() {
		super();
	}

	public TicketService(int tickets) {
		super();
		this.tickets = tickets;
	}

	
	public void sellTickets() throws Exception {
		try {
			/*小测验-lock()方法比tryLock()快
			  if(lock.tryLock()) {
				if(tickets > 0) {
					tickets-- ;
					System.out.println(Thread.currentThread().getName()+"窗口卖了1张票,待卖票数:"+tickets);
				}else {
					long time = System.currentTimeMillis() - TimeTools.getStartTime();
					throw new Exception(Thread.currentThread().getName()+"窗口:卖完了!  耗时:" + time + "毫秒!" );
				}
				tryLock 耗时:14112毫秒
				lock  	耗时:6302毫秒!

			}*/
			lock.lock();
			if(tickets > 0) {
				tickets-- ;
				System.out.println(Thread.currentThread().getName()+"窗口卖了1张票,待卖票数:"+tickets);
			}else {
				long time = System.currentTimeMillis() - TimeTools.getStartTime();
				throw new Exception(Thread.currentThread().getName()+"窗口:卖完了!  耗时:" + time + "毫秒!" );
			}
		} catch (Exception e) {
			throw new Exception(e.getMessage());
		} finally {
			if(lock.isHeldByCurrentThread()) {
				lock.unlock();
			}
		}
	}
}

package com.cc.sellticket3;
/*
 * 记录开始时间工具
 */
public class TimeTools {
	private static long startTime = 0;

	public static long getStartTime() {
		return startTime;
	}
	public static void setStartTime(long startTime) {
		TimeTools.startTime = startTime;
	}
	
}
package com.cc.sellticket3;
/*
 * 多开几个窗口卖票
 */
public class SellTicketThread extends Thread{
	private TicketService service;

	public SellTicketThread(TicketService service) {
		super();
		this.service = service;
	}
	
	@Override
	public void run() {
		while(true) {
			try {
				Thread.sleep(300);
			} catch (InterruptedException e) {
				e.printStackTrace();
			}
			
			try {
				service.sellTickets();
			} catch (Exception e) {
				System.err.println(e.getMessage());
				break;
			}
			
		}
	}

}

package com.cc.sellticket3;
/*
 * 模拟卖票运行
 */
public class Run {
	public static void main(String[] args) throws InterruptedException {
		//今天卖票服务一共卖80张票--一般50张
		TicketService service = new TicketService(80);
		//开始卖票时间
		TimeTools.setStartTime(System.currentTimeMillis());
		//卖票一直到结束
		SellTicketThread t1 = new SellTicketThread(service);
		t1.setName("1号");
		SellTicketThread t2 = new SellTicketThread(service);
		t2.setName("2号");
		SellTicketThread t3 = new SellTicketThread(service);
		t3.setName("3号");
		SellTicketThread t4 = new SellTicketThread(service);
		t4.setName("4号");
		
		t1.start();
		t2.start();
		t3.start();
		t4.start();
	}
}

运行结果:
1号窗口卖了1张票,待卖票数:79
4号窗口卖了1张票,待卖票数:78
2号窗口卖了1张票,待卖票数:77
3号窗口卖了1张票,待卖票数:76
3号窗口卖了1张票,待卖票数:75
4号窗口卖了1张票,待卖票数:74
2号窗口卖了1张票,待卖票数:73
1号窗口卖了1张票,待卖票数:72
4号窗口卖了1张票,待卖票数:71
1号窗口卖了1张票,待卖票数:70
2号窗口卖了1张票,待卖票数:69
3号窗口卖了1张票,待卖票数:68
1号窗口卖了1张票,待卖票数:67
3号窗口卖了1张票,待卖票数:66
2号窗口卖了1张票,待卖票数:65
4号窗口卖了1张票,待卖票数:64
1号窗口卖了1张票,待卖票数:63
3号窗口卖了1张票,待卖票数:62
4号窗口卖了1张票,待卖票数:61
2号窗口卖了1张票,待卖票数:60
4号窗口卖了1张票,待卖票数:59
3号窗口卖了1张票,待卖票数:58
1号窗口卖了1张票,待卖票数:57
2号窗口卖了1张票,待卖票数:56
2号窗口卖了1张票,待卖票数:55
3号窗口卖了1张票,待卖票数:54
4号窗口卖了1张票,待卖票数:53
1号窗口卖了1张票,待卖票数:52
2号窗口卖了1张票,待卖票数:51
3号窗口卖了1张票,待卖票数:50
1号窗口卖了1张票,待卖票数:49
4号窗口卖了1张票,待卖票数:48
2号窗口卖了1张票,待卖票数:47
3号窗口卖了1张票,待卖票数:46
4号窗口卖了1张票,待卖票数:45
1号窗口卖了1张票,待卖票数:44
4号窗口卖了1张票,待卖票数:43
2号窗口卖了1张票,待卖票数:42
1号窗口卖了1张票,待卖票数:41
3号窗口卖了1张票,待卖票数:40
3号窗口卖了1张票,待卖票数:39
1号窗口卖了1张票,待卖票数:38
2号窗口卖了1张票,待卖票数:37
4号窗口卖了1张票,待卖票数:36
2号窗口卖了1张票,待卖票数:35
3号窗口卖了1张票,待卖票数:34
4号窗口卖了1张票,待卖票数:33
1号窗口卖了1张票,待卖票数:32
1号窗口卖了1张票,待卖票数:31
3号窗口卖了1张票,待卖票数:30
2号窗口卖了1张票,待卖票数:29
4号窗口卖了1张票,待卖票数:28
2号窗口卖了1张票,待卖票数:27
3号窗口卖了1张票,待卖票数:26
1号窗口卖了1张票,待卖票数:25
4号窗口卖了1张票,待卖票数:24
2号窗口卖了1张票,待卖票数:23
3号窗口卖了1张票,待卖票数:22
4号窗口卖了1张票,待卖票数:21
1号窗口卖了1张票,待卖票数:20
2号窗口卖了1张票,待卖票数:19
4号窗口卖了1张票,待卖票数:18
3号窗口卖了1张票,待卖票数:17
1号窗口卖了1张票,待卖票数:16
2号窗口卖了1张票,待卖票数:15
3号窗口卖了1张票,待卖票数:14
1号窗口卖了1张票,待卖票数:13
4号窗口卖了1张票,待卖票数:12
2号窗口卖了1张票,待卖票数:11
3号窗口卖了1张票,待卖票数:10
1号窗口卖了1张票,待卖票数:9
4号窗口卖了1张票,待卖票数:8
2号窗口卖了1张票,待卖票数:7
1号窗口卖了1张票,待卖票数:6
4号窗口卖了1张票,待卖票数:5
3号窗口卖了1张票,待卖票数:4
2号窗口卖了1张票,待卖票数:3
3号窗口卖了1张票,待卖票数:2
4号窗口卖了1张票,待卖票数:1
1号窗口卖了1张票,待卖票数:0
3号窗口:卖完了! 耗时:6302毫秒!
4号窗口:卖完了! 耗时:6302毫秒!
2号窗口:卖完了! 耗时:6302毫秒!
1号窗口:卖完了! 耗时:6302毫秒!

知识点:
ReentrantLock类的lock()和unlock()方法控制对象锁。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值