執行緒鎖 -賣票機制

歷精圖治發表於2018-11-22
public class TicketService {
	ArrayList<String> list = new ArrayList<>()  ;
	
	//private Vector list =  new Vector (); vector中方法 remove  和size 是有鎖 
	
		public TicketService(){
			list.add("01車0A號");
			list.add("01車0B號");
			list.add("01車0C號");
			list.add("01車0D號");
			list.add("01車0E號");
			list.add("01車0F號");
			
			list.add("02車0A號");
			list.add("02車0B號");
			list.add("02車0C號");
			list.add("02車0D號");
			list.add("02車0E號");
			list.add("02車0F號");
			
		}
		
		public void sale () {
			//this or all都可以  
			//public void synchronized sale () {
			synchronized(list) {
				if(list.size()>0) {
					String number = list.remove(0);
						System.out.println(number);
					}else {
						System.out.println("已經賣光了");
					}
			}
			
		}

		public boolean hasTicket() {
			return list.size()>0;
		}
}


/***
 * 賣票:兩個視窗同時賣票  
 * 出現了兩個視窗賣出 ,票號相同的票
 *原因:兩個執行緒操作了同一個資源 共享資料list 這就會有執行緒問題 
 *Java  中提供了一種方式解決執行緒安全問題  
 *	同步程式碼塊  
 *sychronized(同步監視器物件){
 *    需要同步程式碼 
 *}
 *同步監視器物件的要求  
 *1)同步監視器物件的型別 可以是任意的引用資料的型別 
 *2)使用共享資料的這個多執行緒要用了同一個監視器物件
 *同步方法:
 *sychronized() throw
 *
 *同步監視器物件放在方法上: 
 *非靜態方法:this
 *靜態方法:當前類class 
 *也必須保證多個執行緒用同一個監視器物件 this也要是同一個 
 *依據:哪些程式碼執行過程中,不允許其它執行緒插入進來 
 */
public class TestSale {
	 public static void main(String[] args) {
		Window window1 = new Window("視窗一") ;
		Window window2 = new Window("視窗二") ;
		window1.start(); 
		window2.start(); 
	}
}

class Window extends Thread {
	 static TicketService ts     = new TicketService() ;
	 //TicketService ts     = new TicketService() ;  錯誤 因為tickerservice 是需要一個物件 
	 public Window (String name) {
		 super(name);
	 }
//	public  synchronized void run  錯誤的原因是因為非靜態方法是鎖定的this  但是這個this 是windows1  windows2 是不同的物件 
	 public   void run () {
		while(ts.hasTicket()) {
			ts.sale(); 
		}
	}
}

在這裡插入圖片描述

![在這裡插入圖片描述](https://img-blog.csdnimg.cn/2018112215124247.png?x-oss-process=image/watermark, type_ZmFuZ3poZW5naGVpdGk,shadow_10,text_aHR0cHM6Ly9ibG9nLmNzZG4ubmV0L1BZb3VMaW5nMTIzNDU2Nzg5,size_16,color_FFFFFF,t_70)
在這裡插入圖片描述

相關文章