
在Java多线程编程中,保证多个线程只有一个线程能够访问某个方法或者某个代码块,主要是访问方法或者代码块中的数据。java提供了synchronized的机制来实现。下面介绍下synchronized的使用方法和原理。
synchronized使用方法
synchronized修饰实例方法,这样的含义是锁住当前实例对象,多个线程运行该方法,只有一个线程能够获得该实例的锁,执行方法。例子:

synchronized修饰静态方法,这样的含义是锁住当前类对象,此时与创建的对象无关,只有一个线程能够该类对象的锁。

synchronized锁住代码块,对指定的对象加锁,那么多个线程中,只有一个线程能够获得该对象的锁。

synchronized实现原理
我们写一段简单的代码进行验证synchronized的底层实现原理。使用javap工具查看生成的class文件信息,观察具体的实现。

javap观察到的结果信息:

我们可以看到synchronized同步代码块的实现是依赖monitorenter和monitorexit指令,分别方法在方法的进入之前和之后。synchronized同步方法的话,则是通过在所编译出的class文件,将class文件的方法表中将该方法的access_flags字段中的synchronized标志设置为ACC_SYNCHRONIZED,这样在调用该方法时,JVM就会将该Class对象设置为锁对象。
synchronized的可重入性
在实际应用开发中,同一个线程会频繁访问synchronized修饰的代码块,此时JVM将其设置为可重入锁,同一个线程是可以再次访问的
synchronized与中断
synchronized是jvm内置锁,是非中断锁,必须等待线程执行完成才会释放锁,这是一个非常需要注意的点
synchronized等待唤醒
这里的是指调用使用wait,唤醒调用notify/notifyAll,如果在synchronized修饰的代码块中执行,必须对synchronized锁住的对象进行wait
,notify, notifyAll,否则就会抛出IllegalMonitorStateException异常

如果是是对图中的 info.wait(); info.notify(); 则是正确的
synchronized继承问题
synchronized关键字不具备继承性,父类定义了方法A用synchronized修饰,子类继承父类,同样调用方法A,此时子类调用A是不具备同步功能的,需要添加synchronized关键字。主要是因为:synchronized非函数签名,因此无法被继承,所以无法保证子类调用同步.
以上总结:
synchronized修饰实例方法,这样的含义是锁住当前实例对象synchronized修饰静态方法,这样的含义是锁住当前类对象synchronized锁住代码块,对指定的对象加锁synchronized是可以重入锁,无法被中断,而且在代码块中执行wait notify notifyAll,必须是锁住的对象才可以synchronized不具备继承特性。
【关键词:青岛Java培训机构,正规Java开发培训,学Java开发多少钱,Java培训哪家好,中享思途】