首页 > 代码库 > 线程的同步synchronized

线程的同步synchronized

一个Java程序的多线程之间可以共享数据
当线程以异步方式访问共享数据时,有时候是不安全的或者不和逻辑的。比如卖火车票,同一时刻一个线程在读取数据,另外一个线程在处理数据,当处理数据的线程没有等到读取数据的线程读取完毕就去处理数据,必然得到错误的处理结果。

卖火车票Demo:
class MyThread implements Runnable{
	private int ticket = 5 ;	// 假设一共有5张票
	public void run(){
		for(int i=0;i<100;i++){
			if(ticket>0){	// 还有票
				try{
					Thread.sleep(300) ;	// 加入延迟
				}catch(InterruptedException e){
					e.printStackTrace() ;
				}
				System.out.println("卖票:ticket = " + ticket-- );
			}
		}
	}
};
public class SyncDemo01{
	public static void main(String args[]){
		MyThread mt = new MyThread() ;	// 定义线程对象
		Thread t1 = new Thread(mt) ;	// 定义Thread对象
		Thread t2 = new Thread(mt) ;	// 定义Thread对象
		Thread t3 = new Thread(mt) ;	// 定义Thread对象
		t1.start() ;
		t2.start() ;
		t3.start() ;
	}
};
运行有可能出现以下结果:
.......
卖票:ticket=1
卖票:ticket=0
卖票:ticket=-1

Java 编程语言提供了一种简单的机制来防止发生这种覆盖。每个对象在运行时都有一个关联的锁。这个锁可通过为方法添加关键字synchronized 来获得。同步有两种方式:同步块和同步方法


同步块:对易发生冲突的语句块加锁

class MyThread implements Runnable{
	private int ticket = 5 ;	// 假设一共有5张票
	public void run(){
		for(int i=0;i<100;i++){
			synchronized(this){	// 要对当前对象进行同步
				if(ticket>0){	// 还有票
					try{
						Thread.sleep(300) ;	// 加入延迟
					}catch(InterruptedException e){
						e.printStackTrace() ;
					}
					System.out.println("卖票:ticket = " + ticket-- );
				}
			}
		}
	}
};
public class SyncDemo02{
	public static void main(String args[]){
		MyThread mt = new MyThread() ;	// 定义线程对象
		Thread t1 = new Thread(mt) ;	// 定义Thread对象
		Thread t2 = new Thread(mt) ;	// 定义Thread对象
		Thread t3 = new Thread(mt) ;	// 定义Thread对象
		t1.start() ;
		t2.start() ;
		t3.start() ;
	}
};


同步方法:对易发生冲突的方法块加锁

class MyThread implements Runnable{
	private int ticket = 5 ;	// 假设一共有5张票
	public void run(){
		for(int i=0;i<100;i++){
			this.sale() ;	// 调用同步方法
		}
	}
	public synchronized void sale(){	// 声明同步方法
		if(ticket>0){	// 还有票
			try{
				Thread.sleep(300) ;	// 加入延迟
			}catch(InterruptedException e){
				e.printStackTrace() ;
			}
			System.out.println("卖票:ticket = " + ticket-- );
		}

	}
};
public class SyncDemo03{
	public static void main(String args[]){
		MyThread mt = new MyThread() ;	// 定义线程对象
		Thread t1 = new Thread(mt) ;	// 定义Thread对象
		Thread t2 = new Thread(mt) ;	// 定义Thread对象
		Thread t3 = new Thread(mt) ;	// 定义Thread对象
		t1.start() ;
		t2.start() ;
		t3.start() ;
	}
};