加鎖和釋放鎖的原理
當方法執行完后或者拋出異常后,都會釋放鎖

method1等價於method2,因為method1執行完以后會自動釋放鎖,而么method2使用lock.unlock()釋放鎖
反編譯看monitor指令
被 synchronized 關鍵字修飾的方法、代碼塊,就是 monitor 機制的臨界區
進入鎖和釋放鎖是基於monitor來實現的 同步方法和同步代碼塊,monitor有兩個指令,monitorenter會插入到同步代碼塊的位置,monitorexit會插入到方法塊結束和退出的時候,可能有多個monitorexit對應一個monitorenter,因為退出可以是方法結束或者拋出異常

通過反編譯(把.class文件轉為.java)
編譯:

反編譯:


Monditorenter和Monditorexit
實際上一個對象和一個monitor相關聯,一個monitorde lock鎖只能被一個線程再同一時間獲得
Monditorenter的三種情況
1.當monitor計數器為0,代表沒有被獲得,然后線程立馬獲得該Monitor,並把計數器加1,當別的線程想進來,但是看到計數器為1,就代表已經被其他線程占有,就只有等待
2.如果Monitor已經拿到了鎖的所有權,又重入了鎖,則monitor會累加
3.如果monitor被其他線程占用了,當我想去獲取的時候,不能獲取到,只能處於阻塞狀態,當計數器為0才能再次嘗試去獲取鎖
Monditorexit的作用是釋放鎖,前提是要先擁有此鎖,原理是將計數器減1,減1如果monitor為0,則對象不再擁有對鎖的所有權,就是解鎖,如果不是1,則證明是重入進來的,繼續持有鎖,
可重入原理

可見性原理

