线程同步7种方法

时间:2021-08-06 15:45:01

注意:线程同步中尽管所个线程之间  加锁的方式不同(同步方法,同步代码块,Lock)、加锁的代码也不相同

   但是只要锁对象相同,那么同一时间就能执行一个线程,实现同步

 线程状态一点知识:覆写run方法只是把线程变成就绪状态,真正进入运行状态的是调用start方法

一、同步方法

synchronized

    synchronized 关键字用于保护共享数据

    普通同步方法:锁对象(内置锁):默认this

    静态同步方法:锁对象:默认当前的类对象  对静态方法的同步本质上是对类的同步(静态方法本质上是属于类的方法,而不是对象上的方法)

    synchronized不能修饰抽象方法!

  但是注意使用非this同步代码块的时候,里面的object不要用String类型的,因为大家都知道JVM具有String常量池缓存的功能,所以使用String类型可能产生问题。因为string字符串在常量池中有缓存,就没有唯一性了

 二、同步代码块

  注意:synchronized( ){ }括号中不能是引用数据类型的对象及null对象  得是类对象(唯一性)

    使用一个引用对象的实例变量作为锁并不是一个好的选择,因为同步块在执行过程中可能会改变它的值,其中就包括将其设置为null,而对一个null对象加锁会产生异常,并且对不同的对象加锁也违背了同步的初衷!

 

疑问:如果一个对象既有同步方法,又有同步块,那么当其中任意一个同步方法或者同步块被某个线程执行时,这个对象就被锁定了,其他线程无法在此时访问这个对象的同步方法,也不能执行同步块。

三、wait与notify

wait():使一个线程处于等待状态,并且释放所持有的对象的lock。

sleep():使一个正在运行的线程处于睡眠状态,是一个静态方法,调用此方法要捕捉InterruptedException异常。
notify():唤醒一个处于等待状态的线程,注意的是在调用此方法的时候,并不能确切的唤醒某一个等待状态的线程,而是由JVM确定唤醒哪个线程,而且不是按优先级。
notifyAll():唤醒所有处入等待状态的线程,注意并不是给所有唤醒线程一个对象的锁,而是让它们竞争。