首页 > 代码库 > 线程问题——同步和死锁

线程问题——同步和死锁

【问题引出】:比如说对于买票系统,有下面的代码:

 1 class hello implements Runnable { 2     private static int count=5; 3     public void run() { 4         for(int i=0;i<10;++i){ 5             if(count>0){ 6                 try{ 7                     Thread.sleep(1000); 8                 }catch(InterruptedException e){ 9                     e.printStackTrace();10                 }11                 System.out.println(count--);12             }13         }14     }15  16     public static void main(String[] args) {17         hello he=new hello();18         Thread h1=new Thread(he);19         Thread h2=new Thread(he);20         Thread h3=new Thread(he);21         h1.start();22         h2.start();23         h3.start();24     }25 }

【运行结果】

5
4
3
2
1
0
-1

这里出现了-1,显然这个是错的。,应该票数不能为负值。

如果想解决这种问题,就需要使用同步。所谓同步就是在统一时间段中只有有一个线程运行,

其他的线程必须等到这个线程结束之后才能继续执行。

【使用线程同步解决问题】

采用同步的话,可以使用同步代码块同步方法两种来完成。

(一)同步代码块

语法格式:

synchronized(同步对象){

 //需要同步的代码

}

但是一般都把当前对象this作为同步对象。

比如对于上面的买票的问题,如下(修改run方法):

public void run() {        for(int i=0;i<10;++i){            synchronized(this){                if(count>0){                    try{                        Thread.sleep(1000);                    }catch(InterruptedException e){                        e.printStackTrace();                    }                    System.out.println(count--);                }            }        }    }

【运行结果】:(每一秒输出一个结果)

5

4

3

2

1

(二)同步方法

语法格式为

synchronized 方法返回类型方法名(参数列表){

    // 其他代码

}

修改run方法

public void run() {        for (int i = 0; i < 10; ++i) {            sale();        }    }     public synchronized void sale() {        if (count > 0) {            try {                Thread.sleep(1000);            } catch (InterruptedException e) {                e.printStackTrace();            }            System.out.println(count--);        }    }

运行结果同上。

提醒一下,当多个线程共享一个资源的时候需要进行同步,但是过多的同步可能导致死锁

 

线程问题——同步和死锁