Java 骞跺彂锛氬唴缃攣 Synchronized
Posted
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了Java 骞跺彂锛氬唴缃攣 Synchronized相关的知识,希望对你有一定的参考价值。
鏍囩锛?a href='http://www.mamicode.com/so/1/code' title='code'>code string 涓€鍙ヨ瘽 浣跨敤鍦烘櫙 绯荤粺 鍙傛暟 鐜拌薄 瀹冪殑
鍦ㄥ绾跨▼缂栫▼涓紝绾跨▼瀹夊叏闂鏄竴涓渶涓哄叧閿殑闂锛屽叾鏍稿績姒傚康灏卞湪浜庢纭€э紝鍗冲綋澶氫釜绾跨▼璁块棶鏌愪竴鍏变韩銆佸彲鍙樻暟鎹椂锛屽缁堥兘涓嶄細瀵艰嚧鏁版嵁鐮村潖浠ュ強鍏朵粬涓嶈鍑虹幇鐨勭粨鏋溿€傝€屾墍鏈夌殑骞跺彂妯″紡鍦ㄨВ鍐宠繖涓棶棰樻椂锛岄噰鐢ㄧ殑鏂规閮芥槸搴忓垪鍖栬闂复鐣岃祫婧?銆傚湪 Java 涓紝鎻愪緵浜嗕袱绉嶆柟寮忔潵瀹炵幇鍚屾浜掓枼璁块棶锛歴ynchronized 鍜?Lock銆傛湰鏂囬拡瀵?synchronized 鍐呯疆閿?璇︾粏璁ㄨ浜嗗叾鍦?Java 骞跺彂 涓殑搴旂敤锛屽寘鎷畠鐨勫叿浣撲娇鐢ㄥ満鏅紙鍚屾鏂规硶銆佸悓姝ヤ唬鐮佸潡銆佸疄渚嬪璞¢攣 鍜?Class 瀵硅薄閿侊級銆佸彲閲嶅叆鎬?鍜?娉ㄦ剰浜嬮」銆?/p>
涓€. 绾跨▼瀹夊叏闂
銆€銆€鍦ㄥ崟绾跨▼涓笉浼氬嚭鐜扮嚎绋嬪畨鍏ㄩ棶棰橈紝鑰屽湪澶氱嚎绋嬬紪绋嬩腑锛屾湁鍙兘浼氬嚭鐜板悓鏃惰闂悓涓€涓?鍏变韩銆佸彲鍙樿祫婧?鐨勬儏鍐碉紝杩欑璧勬簮鍙互鏄細涓€涓彉閲忋€佷竴涓璞°€佷竴涓枃浠剁瓑銆傜壒鍒敞鎰忎袱鐐癸紝
- 鍏变韩锛?鎰忓懗鐫€璇ヨ祫婧愬彲浠ョ敱澶氫釜绾跨▼鍚屾椂璁块棶锛?/li>
- 鍙彉锛?鎰忓懗鐫€璇ヨ祫婧愬彲浠ュ湪鍏剁敓鍛藉懆鏈熷唴琚慨鏀广€?/li>
銆€鎵€浠ワ紝褰撳涓嚎绋嬪悓鏃惰闂繖绉嶈祫婧愮殑鏃跺€欙紝灏变細瀛樺湪涓€涓棶棰橈細
銆€銆€銆€鐢变簬姣忎釜绾跨▼鎵ц鐨勮繃绋嬫槸涓嶅彲鎺х殑锛屾墍浠ラ渶瑕侀噰鐢ㄥ悓姝ユ満鍒舵潵鍗忓悓瀵瑰璞″彲鍙樼姸鎬佺殑璁块棶銆?
涓句釜 鏁版嵁鑴忚 鐨勪緥瀛愶細
//璧勬簮绫?/span> class PublicVar public String username = "A"; public String password = "AA"; //鍚屾瀹炰緥鏂规硶 public synchronized void setValue(String username, String password) try this.username = username; Thread.sleep(5000); this.password = password; System.out.println("method=setValue " +"\t" + "threadName=" + Thread.currentThread().getName() + "\t" + "username=" + username + ", password=" + password); catch (InterruptedException e) e.printStackTrace(); //闈炲悓姝ュ疄渚嬫柟娉?/span> public void getValue() System.out.println("method=getValue " + "\t" + "threadName=" + Thread.currentThread().getName()+ "\t" + " username=" + username + ", password=" + password); //绾跨▼绫?/span> class ThreadA extends Thread private PublicVar publicVar; public ThreadA(PublicVar publicVar) super(); this.publicVar = publicVar; @Override public void run() super.run(); publicVar.setValue("B", "BB"); //娴嬭瘯绫?/span> public class Test public static void main(String[] args) try //涓寸晫璧勬簮 PublicVar publicVarRef = new PublicVar(); //鍒涘缓骞跺惎鍔ㄧ嚎绋?/span> ThreadA thread = new ThreadA(publicVarRef); thread.start(); Thread.sleep(200);// 鎵撳嵃缁撴灉鍙楁鍊煎ぇ灏忓奖鍝? //鍦ㄤ富绾跨▼涓皟鐢?/span> publicVarRef.getValue(); catch (InterruptedException e) e.printStackTrace(); /* Output ( 鏁版嵁浜ゅ弶 ): method=getValue threadName=main username=B, password=AA method=setValue threadName=Thread-0 username=B, password=BB */
銆€鐢辩▼搴忚緭鍑哄彲鐭ワ紝铏界劧鍦ㄥ啓鎿嶄綔杩涜浜嗗悓姝ワ紝浣嗗湪璇绘搷浣滀笂浠嶇劧鏈夊彲鑳藉嚭鐜颁竴浜涙剰鎯充笉鍒扮殑鎯呭喌锛屼緥濡備笂闈㈡墍绀虹殑 鑴忚銆傚彂鐢?鑴忚 鐨勬儏鍐垫槸鍦ㄦ墽琛岃鎿嶄綔鏃讹紝鐩稿簲鐨勬暟鎹凡琚叾浠栫嚎绋?閮ㄥ垎淇敼 杩囷紝瀵艰嚧 鏁版嵁浜ゅ弶 鐨勭幇璞′骇鐢熴€?/p>
銆€銆€杩欏叾瀹炲氨鏄竴涓嚎绋嬪畨鍏ㄩ棶棰橈紝鍗冲涓嚎绋嬪悓鏃惰闂竴涓祫婧愭椂锛屼細瀵艰嚧绋嬪簭杩愯缁撴灉骞朵笉鏄兂鐪嬪埌鐨勭粨鏋溿€傝繖閲岄潰锛岃繖涓祫婧愯绉颁负锛氫复鐣岃祫婧愩€備篃灏辨槸璇达紝褰撳涓嚎绋嬪悓鏃惰闂复鐣岃祫婧愶紙涓€涓璞★紝瀵硅薄涓殑灞炴€э紝涓€涓枃浠讹紝涓€涓暟鎹簱绛夛級鏃讹紝灏卞彲鑳戒細浜х敓绾跨▼瀹夊叏闂銆?/p>
銆€銆€涓嶈繃锛屽綋澶氫釜绾跨▼鎵ц涓€涓柟娉曟椂锛岃鏂规硶鍐呴儴鐨勫眬閮ㄥ彉閲忓苟涓嶆槸涓寸晫璧勬簮锛屽洜涓鸿繖浜涘眬閮ㄥ彉閲忔槸鍦ㄦ瘡涓嚎绋嬬殑绉佹湁鏍堜腑锛屽洜姝や笉鍏锋湁鍏变韩鎬э紝涓嶄細瀵艰嚧绾跨▼瀹夊叏闂銆?/p>
浜? 濡備綍瑙e喅绾跨▼瀹夊叏闂
銆€銆€瀹為檯涓婏紝鎵€鏈夌殑骞跺彂妯″紡鍦ㄨВ鍐崇嚎绋嬪畨鍏ㄩ棶棰樻椂锛岄噰鐢ㄧ殑鏂规閮芥槸 搴忓垪鍖栬闂复鐣岃祫婧?銆傚嵆鍦ㄥ悓涓€鏃跺埢锛屽彧鑳芥湁涓€涓嚎绋嬭闂复鐣岃祫婧愶紝涔熺О浣?鍚屾浜掓枼璁块棶銆傛崲鍙ヨ瘽璇达紝灏辨槸鍦ㄨ闂复鐣岃祫婧愮殑浠g爜鍓嶉潰鍔犱笂涓€涓攣锛屽綋璁块棶瀹屼复鐣岃祫婧愬悗閲婃斁閿侊紝璁╁叾浠栫嚎绋嬬户缁闂€?/p>
銆€銆€鍦?Java 涓紝鎻愪緵浜嗕袱绉嶆柟寮忔潵瀹炵幇鍚屾浜掓枼璁块棶锛歴ynchronized 鍜?Lock銆傛湰鏂囦富瑕佽杩?synchronized 鐨勪娇鐢ㄦ柟娉?
涓? synchronized 鍚屾鏂规硶鎴栬€呭悓姝ュ潡
銆€銆€鍦ㄤ簡瑙?synchronized 鍏抽敭瀛楃殑浣跨敤鏂规硶涔嬪墠锛屾垜浠厛鏉ョ湅涓€涓蹇碉細浜掓枼閿侊紝鍗?鑳藉埌杈惧埌浜掓枼璁块棶鐩殑鐨勯攣銆備妇涓畝鍗曠殑渚嬪瓙锛屽鏋滃涓寸晫璧勬簮鍔犱笂浜掓枼閿侊紝褰撲竴涓嚎绋嬪湪璁块棶璇ヤ复鐣岃祫婧愭椂锛屽叾浠栫嚎绋嬩究鍙兘绛夊緟銆?/p>
銆€銆€鍦?Java 涓紝鍙互浣跨敤 synchronized 鍏抽敭瀛楁潵鏍囪涓€涓柟娉曟垨鑰呬唬鐮佸潡锛屽綋鏌愪釜绾跨▼璋冪敤璇ュ璞$殑synchronized鏂规硶鎴栬€呰闂畇ynchronized浠g爜鍧楁椂锛岃繖涓嚎绋嬩究鑾峰緱浜嗚瀵硅薄鐨勯攣锛屽叾浠栫嚎绋嬫殏鏃舵棤娉曡闂繖涓柟娉曪紝鍙湁绛夊緟杩欎釜鏂规硶鎵ц瀹屾瘯鎴栬€呬唬鐮佸潡鎵ц瀹屾瘯锛岃繖涓嚎绋嬫墠浼氶噴鏀捐瀵硅薄鐨勯攣锛屽叾浠栫嚎绋嬫墠鑳芥墽琛岃繖涓柟娉曟垨鑰呬唬鐮佸潡銆?/p>
銆€銆€涓嬮潰杩欐浠g爜涓袱涓嚎绋嬪垎鍒皟鐢╥nsertData瀵硅薄鎻掑叆鏁版嵁锛?br />1) synchronized鏂规硶
public class Test public static void main(String[] args) final InsertData insertData = new InsertData(); // 鍚姩绾跨▼ 1 new Thread() public void run() insertData.insert(Thread.currentThread()); ; .start(); // 鍚姩绾跨▼ 2 new Thread() public void run() insertData.insert(Thread.currentThread()); ; .start(); class InsertData // 鍏变韩銆佸彲鍙樿祫婧?/span> private ArrayList<Integer> arrayList = new ArrayList<Integer>(); //瀵瑰叡浜彲鍙樿祫婧愮殑璁块棶 public void insert(Thread thread) for(int i=0;i<5;i++) System.out.println(thread.getName()+"鍦ㄦ彃鍏ユ暟鎹?+i); arrayList.add(i); /* Output: Thread-0鍦ㄦ彃鍏ユ暟鎹? Thread-1鍦ㄦ彃鍏ユ暟鎹? Thread-0鍦ㄦ彃鍏ユ暟鎹? Thread-0鍦ㄦ彃鍏ユ暟鎹? Thread-1鍦ㄦ彃鍏ユ暟鎹? Thread-1鍦ㄦ彃鍏ユ暟鎹? */
鏍规嵁杩愯缁撴灉灏卞彲浠ョ湅鍑猴紝杩欎袱涓嚎绋嬪湪鍚屾椂鎵цinsert()鏂规硶銆傝€屽鏋滃湪insert()鏂规硶鍓嶉潰鍔犱笂鍏抽敭瀛梥ynchronized 鐨勮瘽锛岃繍琛岀粨鏋滀负锛?/p>
class InsertData private ArrayList<Integer> arrayList = new ArrayList<Integer>(); public synchronized void insert(Thread thread) for(int i=0;i<5;i++) System.out.println(thread.getName()+"鍦ㄦ彃鍏ユ暟鎹?+i); arrayList.add(i); /* Output: Thread-0鍦ㄦ彃鍏ユ暟鎹? Thread-0鍦ㄦ彃鍏ユ暟鎹? Thread-0鍦ㄦ彃鍏ユ暟鎹? Thread-1鍦ㄦ彃鍏ユ暟鎹? Thread-1鍦ㄦ彃鍏ユ暟鎹? Thread-1鍦ㄦ彃鍏ユ暟鎹? */
銆€浠庝互涓婅緭鍑虹粨鏋滃彲浠ョ湅鍑猴紝Thread-1 鎻掑叆鏁版嵁鏄瓑 Thread-0 鎻掑叆瀹屾暟鎹箣鍚庢墠杩涜鐨勩€傝鏄?Thread-0 鍜?Thread-1 鏄『搴忔墽琛?insert() 鏂规硶鐨勩€傝繖灏辨槸 synchronized 鍏抽敭瀛楀鏂规硶鐨勪綔鐢ㄣ€?/p>
銆€銆€涓嶈繃闇€瑕佹敞鎰忎互涓嬩笁鐐癸細
銆€銆€1锛夊綋涓€涓嚎绋嬫鍦ㄨ闂竴涓璞$殑 synchronized 鏂规硶锛岄偅涔堝叾浠栫嚎绋嬩笉鑳借闂瀵硅薄鐨勫叾浠?synchronized 鏂规硶銆傝繖涓師鍥犲緢绠€鍗曪紝鍥犱负涓€涓璞″彧鏈変竴鎶婇攣锛屽綋涓€涓嚎绋嬭幏鍙栦簡璇ュ璞$殑閿佷箣鍚庯紝鍏朵粬绾跨▼鏃犳硶鑾峰彇璇ュ璞$殑閿侊紝鎵€浠ユ棤娉曡闂瀵硅薄鐨勫叾浠杝ynchronized鏂规硶銆?/p>
銆€銆€2锛夊綋涓€涓嚎绋嬫鍦ㄨ闂竴涓璞$殑 synchronized 鏂规硶锛岄偅涔堝叾浠栫嚎绋嬭兘璁块棶璇ュ璞$殑闈?synchronized 鏂规硶銆傝繖涓師鍥犲緢绠€鍗曪紝璁块棶闈?synchronized 鏂规硶涓嶉渶瑕佽幏寰楄瀵硅薄鐨勯攣锛屽亣濡備竴涓柟娉曟病鐢?synchronized 鍏抽敭瀛椾慨楗帮紝璇存槑瀹冧笉浼氫娇鐢ㄥ埌涓寸晫璧勬簮锛岄偅涔堝叾浠栫嚎绋嬫槸鍙互璁块棶杩欎釜鏂规硶鐨勶紝
銆€銆€3锛夊鏋滀竴涓嚎绋?A 闇€瑕佽闂璞?object1 鐨?synchronized 鏂规硶 fun1锛屽彟澶栦竴涓嚎绋?B 闇€瑕佽闂璞?object2 鐨?synchronized 鏂规硶 fun1锛屽嵆浣?object1 鍜?object2 鏄悓涓€绫诲瀷锛夛紝涔熶笉浼氫骇鐢熺嚎绋嬪畨鍏ㄩ棶棰橈紝鍥犱负浠栦滑璁块棶鐨勬槸涓嶅悓鐨勫璞★紝鎵€浠ヤ笉瀛樺湪浜掓枼闂銆?/p>
2) synchronized 鍚屾鍧?/strong>
synchronized 浠g爜鍧楃被浼间簬浠ヤ笅杩欑褰㈠紡锛?/p>
synchronized (lock) //璁块棶鍏变韩鍙彉璧勬簮 ...
褰撳湪鏌愪釜绾跨▼涓墽琛岃繖娈典唬鐮佸潡锛岃绾跨▼浼氳幏鍙栧璞ock鐨勯攣锛屼粠鑰屼娇寰楀叾浠栫嚎绋嬫棤娉曞悓鏃惰闂浠g爜鍧椼€傚叾涓紝lock 鍙互鏄?this锛屼唬琛ㄨ幏鍙栧綋鍓嶅璞$殑閿侊紝涔熷彲浠ユ槸绫讳腑鐨勪竴涓睘鎬э紝浠h〃鑾峰彇璇ュ睘鎬х殑閿併€傜壒鍒湴锛?瀹炰緥鍚屾鏂规硶 涓?synchronized(this)鍚屾鍧?鏄簰鏂ョ殑锛屽洜涓哄畠浠攣鐨勬槸鍚屼竴涓璞°€備絾涓?synchronized(闈瀟his)鍚屾鍧?鏄紓姝ョ殑锛屽洜涓哄畠浠攣鐨勬槸涓嶅悓瀵硅薄銆?br />姣斿涓婇潰鐨刬nsert()鏂规硶鍙互鏀规垚浠ヤ笅涓ょ褰㈠紡锛?/p>
// this 鐩戣鍣?/span> class InsertData private ArrayList<Integer> arrayList = new ArrayList<Integer>(); public void insert(Thread thread) synchronized (this) for(int i=0;i<100;i++) System.out.println(thread.getName()+"鍦ㄦ彃鍏ユ暟鎹?+i); arrayList.add(i); // 瀵硅薄鐩戣鍣?/span> class InsertData private ArrayList<Integer> arrayList = new ArrayList<Integer>(); private Object object = new Object(); public void insert(Thread thread) synchronized (object) for(int i=0;i<100;i++) System.out.println(thread.getName()+"鍦ㄦ彃鍏ユ暟鎹?+i); arrayList.add(i);
浠庝笂闈唬鐮佸彲浠ョ湅鍑猴紝synchronized浠g爜鍧?姣?synchronized鏂规硶 鐨勭矑搴︽洿缁嗕竴浜涳紝浣跨敤璧锋潵涔熺伒娲诲緱澶氥€傚洜涓轰篃璁镐竴涓柟娉曚腑鍙湁涓€閮ㄥ垎浠g爜鍙渶瑕佸悓姝ワ紝濡傛灉姝ゆ椂瀵规暣涓柟娉曠敤synchronized杩涜鍚屾锛屼細褰卞搷绋嬪簭鎵ц鏁堢巼銆傝€屼娇鐢╯ynchronized浠g爜鍧楀氨鍙互閬垮厤杩欎釜闂锛宻ynchronized浠g爜鍧楀彲浠ュ疄鐜板彧瀵归渶瑕佸悓姝ョ殑鍦版柟杩涜鍚屾銆?/p>
3) class 瀵硅薄閿?/strong>
銆€銆€鐗瑰埆鍦帮紝姣忎釜绫讳篃浼氭湁涓€涓攣锛岄潤鎬佺殑 synchronized鏂规硶 灏辨槸浠lass瀵硅薄浣滀负閿併€傚彟澶栵紝瀹冨彲浠ョ敤鏉ユ帶鍒跺 static 鏁版嵁鎴愬憳 锛坰tatic 鏁版嵁鎴愬憳涓嶄笓灞炰簬浠讳綍涓€涓璞★紝鏄被鎴愬憳锛?鐨勫苟鍙戣闂€傚苟涓旓紝濡傛灉涓€涓嚎绋嬫墽琛屼竴涓璞$殑闈瀞tatic synchronized 鏂规硶锛屽彟澶栦竴涓嚎绋嬮渶瑕佹墽琛岃繖涓璞℃墍灞炵被鐨?static synchronized 鏂规硶锛屼篃涓嶄細鍙戠敓浜掓枼鐜拌薄銆傚洜涓鸿闂?static synchronized 鏂规硶鍗犵敤鐨勬槸绫婚攣锛岃€岃闂潪 static synchronized 鏂规硶鍗犵敤鐨勬槸瀵硅薄閿侊紝鎵€浠ヤ笉瀛樺湪浜掓枼鐜拌薄銆備緥濡傦紝
public class Test public static void main(String[] args) final InsertData insertData = new InsertData(); new Thread() @Override public void run() insertData.insert(); .start(); new Thread() @Override public void run() insertData.insert1(); .start(); class InsertData // 闈?static synchronized 鏂规硶 public synchronized void insert() System.out.println("鎵цinsert"); try Thread.sleep(5000); catch (InterruptedException e) e.printStackTrace(); System.out.println("鎵цinsert瀹屾瘯"); // static synchronized 鏂规硶 public synchronized static void insert1() System.out.println("鎵цinsert1"); System.out.println("鎵цinsert1瀹屾瘯"); /* Output: 鎵цinsert 鎵цinsert1 鎵цinsert1瀹屾瘯 鎵цinsert瀹屾瘯 */
鏍规嵁鎵ц缁撴灉锛屾垜浠彲浠ョ湅鍒扮涓€涓嚎绋嬮噷闈㈡墽琛岀殑鏄痠nsert鏂规硶锛屼笉浼氬鑷寸浜屼釜绾跨▼鎵цinsert1鏂规硶鍙戠敓闃诲鐜拌薄銆備笅闈紝鎴戜滑鐪嬩竴涓?synchronized 鍏抽敭瀛楀埌搴曞仛浜嗕粈涔堜簨鎯咃紝鎴戜滑鏉ュ弽缂栬瘧瀹冪殑瀛楄妭鐮佺湅涓€涓嬶紝涓嬮潰杩欐浠g爜鍙嶇紪璇戝悗鐨勫瓧鑺傜爜涓猴細
public class InsertData private Object object = new Object(); public void insert(Thread thread) synchronized (object) public synchronized void insert1(Thread thread) public void insert2(Thread thread)
浠庡弽缂栬瘧鑾峰緱鐨勫瓧鑺傜爜鍙互鐪嬪嚭锛宻ynchronized 浠g爜鍧楀疄闄呬笂澶氫簡 monitorenter 鍜?monitorexit 涓ゆ潯鎸囦护銆?monitorenter鎸囦护鎵ц鏃朵細璁╁璞$殑閿佽鏁板姞1锛岃€宮onitorexit鎸囦护鎵ц鏃朵細璁╁璞$殑閿佽鏁板噺1锛屽叾瀹炶繖涓笌鎿嶄綔绯荤粺閲岄潰鐨凱V鎿嶄綔寰堝儚锛屾搷浣滅郴缁熼噷闈㈢殑PV鎿嶄綔灏辨槸鐢ㄦ潵鎺у埗澶氫釜杩涚▼瀵逛复鐣岃祫婧愮殑璁块棶銆傚浜巗ynchronized鏂规硶锛屾墽琛屼腑鐨勭嚎绋嬭瘑鍒鏂规硶鐨?method_info 缁撴瀯鏄惁鏈?ACC_SYNCHRONIZED 鏍囪璁剧疆锛岀劧鍚庡畠鑷姩鑾峰彇瀵硅薄鐨勯攣锛岃皟鐢ㄦ柟娉曪紝鏈€鍚庨噴鏀鹃攣銆傚鏋滄湁寮傚父鍙戠敓锛岀嚎绋嬭嚜鍔ㄩ噴鏀鹃攣銆?/p>
銆€銆€鏈変竴鐐硅娉ㄦ剰锛氬浜?synchronized鏂规硶 鎴栬€?synchronized浠g爜鍧楋紝褰撳嚭鐜板紓甯告椂锛孞VM浼氳嚜鍔ㄩ噴鏀惧綋鍓嶇嚎绋嬪崰鐢ㄧ殑閿侊紝鍥犳涓嶄細鐢变簬寮傚父瀵艰嚧鍑虹幇姝婚攣鐜拌薄銆傘€€銆€
鍙噸鍏ラ攣鏈€澶х殑浣滅敤鏄伩鍏嶆閿併€?/span>渚嬪锛?/p>
public class Test implements Runnable
// 鍙噸鍏ラ攣娴嬭瘯
public synchronized void get()
System.out.println(Thread.currentThread().getName());
set();
public synchronized void set()
System.out.println(Thread.currentThread().getName());
@Override
public void run()
get();
public static void main(String[] args)
Test test = new Test();
new Thread(test,"Thread-0").start();
new Thread(test,"Thread-1").start();
new Thread(test,"Thread-2").start();
/* Output:
Thread-1
Thread-1
Thread-2
Thread-2
Thread-0
Thread-0
*/
浜? 娉ㄦ剰浜嬮」
public class Test implements Runnable // 鍙噸鍏ラ攣娴嬭瘯 public synchronized void get() System.out.println(Thread.currentThread().getName()); set(); public synchronized void set() System.out.println(Thread.currentThread().getName()); @Override public void run() get(); public static void main(String[] args) Test test = new Test(); new Thread(test,"Thread-0").start(); new Thread(test,"Thread-1").start(); new Thread(test,"Thread-2").start(); /* Output: Thread-1 Thread-1 Thread-2 Thread-2 Thread-0 Thread-0 */
1). 鍐呯疆閿佷笌瀛楃涓插父閲?/strong>
銆€銆€鐢变簬瀛楃涓插父閲忔睜鐨勫師鍥狅紝鍦ㄥぇ澶氭暟鎯呭喌涓嬶紝鍚屾synchronized浠g爜鍧?閮戒笉浣跨敤 String 浣滀负閿佸璞★紝鑰屾敼鐢ㄥ叾浠栵紝姣斿 new Object() 瀹炰緥鍖栦竴涓?Object 瀵硅薄锛屽洜涓哄畠骞朵笉浼氳鏀惧叆缂撳瓨涓€傜湅涓嬮潰鐨勪緥瀛愶細
//璧勬簮绫?/span> class Service public void print(String stringParam) try synchronized (stringParam) while (true) System.out.println(Thread.currentThread().getName()); Thread.sleep(1000); catch (InterruptedException e) e.printStackTrace(); //绾跨▼A class ThreadA extends Thread private Service service; public ThreadA(Service service) super(); this.service = service; @Override public void run() service.print("AA"); //绾跨▼B class ThreadB extends Thread private Service service; public ThreadB(Service service) super(); this.service = service; @Override public void run() service.print("AA"); //娴嬭瘯 public class Run public static void main(String[] args) //涓寸晫璧勬簮 Service service = new Service(); //鍒涘缓骞跺惎鍔ㄧ嚎绋婣 ThreadA a = new ThreadA(service); a.setName("A"); a.start(); //鍒涘缓骞跺惎鍔ㄧ嚎绋婤 ThreadB b = new ThreadB(service); b.setName("B"); b.start(); /* Output (姝婚攣): A A A A ... */
鍑虹幇涓婅堪缁撴灉灏辨槸鍥犱负 String 绫诲瀷鐨勫弬鏁伴兘鏄?“AA”锛屼袱涓嚎绋嬫寔鏈夌浉鍚岀殑閿侊紝鎵€浠?绾跨▼B 濮嬬粓寰椾笉鍒版墽琛岋紝閫犳垚姝婚攣銆傝繘涓€姝ュ湴锛屾墍璋撴閿佹槸鎸囷細 涓嶅悓鐨勭嚎绋嬮兘鍦ㄧ瓑寰呮牴鏈笉鍙兘琚噴鏀剧殑閿侊紝浠庤€屽鑷存墍鏈夌殑浠诲姟閮芥棤娉曠户缁畬鎴愩€?/em>
b). 閿佺殑鏄璞¤€岄潪寮曠敤
銆€銆€鍦ㄥ皢浠讳綍鏁版嵁绫诲瀷浣滀负鍚屾閿佹椂锛岄渶瑕佹敞鎰忕殑鏄紝鏄惁鏈夊涓嚎绋嬪皢鍚屾椂鍘荤珵浜夎閿佸璞★細
銆€銆€1).鑻ュ畠浠皢鍚屾椂绔炰簤鍚屼竴鎶婇攣锛屽垯杩欎簺绾跨▼涔嬮棿灏辨槸鍚屾鐨勶紱
銆€銆€2).鍚﹀垯锛岃繖浜涚嚎绋嬩箣闂村氨鏄紓姝ョ殑銆?/p>
鐪嬩笅闈㈢殑渚嬪瓙:
//璧勬簮绫?/span> class MyService private String lock = "123"; public void testMethod() try synchronized (lock) System.out.println(Thread.currentThread().getName() + " begin " + System.currentTimeMillis()); lock = "456"; Thread.sleep(2000); System.out.println(Thread.currentThread().getName() + " end " + System.currentTimeMillis()); catch (InterruptedException e) e.printStackTrace(); //绾跨▼B class ThreadB extends Thread private MyService service; public ThreadB(MyService service) super(); this.service = service; @Override public void run() service.testMethod(); //绾跨▼A class ThreadA extends Thread private MyService service; public ThreadA(MyService service) super(); this.service = service; @Override public void run() service.testMethod(); //娴嬭瘯 public class Run1 public static void main(String[] args) throws InterruptedException //涓寸晫璧勬簮 MyService service = new MyService(); //绾跨▼A ThreadA a = new ThreadA(service); a.setName("A"); //绾跨▼B ThreadB b = new ThreadB(service); b.setName("B"); a.start(); Thread.sleep(50);// 瀛樺湪50姣 b.start(); /* Output(寰幆): A begin 1484319778766 B begin 1484319778815 A end 1484319780766 B end 1484319780815 */
鐢变笂杩扮粨鏋滃彲鐭ワ紝绾跨▼ A銆丅 鏄紓姝ョ殑銆傚洜涓?0姣杩囧悗锛?绾跨▼B 鍙栧緱鐨勯攣瀵硅薄鏄?“456”锛岃€?绾跨▼A 渚濈劧鎸佹湁鐨勯攣瀵硅薄鏄?“123”銆傛墍浠ワ紝杩欎袱涓嚎绋嬫槸寮傛鐨勩€傝嫢灏嗕笂杩拌鍙?“Thread.sleep(50);” 娉ㄩ噴锛屽垯鏈夛細
//娴嬭瘯 public class Run1 public static void main(String[] args) throws InterruptedException //涓寸晫璧勬簮 MyService service = new MyService(); //绾跨▼A ThreadA a = new ThreadA(service); a.setName("A"); //绾跨▼B ThreadB b = new ThreadB(service); b.setName("B"); a.start(); // Thread.sleep(50);// 瀛樺湪50姣 b.start(); /* Output(寰幆): B begin 1484319952017 B end 1484319954018 A begin 1484319954018 A end 1484319956019 */
鐢变笂杩扮粨鏋滃彲鐭ワ紝绾跨▼ A銆丅 鏄悓姝ョ殑銆傚洜涓虹嚎绋?A銆丅 绔炰簤鐨勬槸鍚屼竴涓攣“123”锛岃櫧鐒跺厛鑾峰緱杩愯鐨勭嚎绋嬪皢 lock 鎸囧悜浜?瀵硅薄“456”锛屼絾缁撴灉杩樻槸鍚屾鐨勩€傚洜涓虹嚎绋?A 鍜?B 鍏卞悓浜夋姠鐨勯攣瀵硅薄鏄?ldquo;123”锛屼篃灏辨槸璇达紝閿佺殑鏄璞¤€岄潪寮曠敤銆?/span>
灏忕粨:
銆€鐢ㄤ竴鍙ヨ瘽鏉ヨ锛宻ynchronized 鍐呯疆閿?鏄竴绉?瀵硅薄閿?(閿佺殑鏄璞¤€岄潪寮曠敤)锛?浣滅敤绮掑害鏄璞?锛屽彲浠ョ敤鏉ュ疄鐜板 涓寸晫璧勬簮鐨勫悓姝ヤ簰鏂ヨ闂?锛屾槸 鍙噸鍏?鐨勩€傜壒鍒湴锛屽浜?涓寸晫璧勬簮 鏈夛細
- 鑻ヨ璧勬簮鏄潤鎬佺殑锛屽嵆琚?static 鍏抽敭瀛椾慨楗帮紝閭d箞璁块棶瀹冪殑鏂规硶蹇呴』鏄悓姝ヤ笖鏄潤鎬佺殑锛宻ynchronized 鍧楀繀椤绘槸 class閿侊紱
- 鑻ヨ璧勬簮鏄潪闈欐€佺殑锛屽嵆娌℃湁琚?static 鍏抽敭瀛椾慨楗帮紝閭d箞璁块棶瀹冪殑鏂规硶蹇呴』鏄悓姝ョ殑锛宻ynchronized 鍧楁槸瀹炰緥瀵硅薄閿侊紱
瀹炶川涓婏紝鍏抽敭瀛梥ynchronized 涓昏鍖呭惈涓や釜鐗瑰緛锛?/p>
- 浜掓枼鎬э細淇濊瘉鍦ㄥ悓涓€鏃跺埢锛屽彧鏈変竴涓嚎绋嬪彲浠ユ墽琛屾煇涓€涓柟娉曟垨鏌愪竴涓唬鐮佸潡锛?/li>
- 鍙鎬э細淇濊瘉绾跨▼宸ヤ綔鍐呭瓨涓殑鍙橀噺涓庡叕鍏卞唴瀛樹腑鐨勫彉閲忓悓姝ワ紝浣垮绾跨▼璇诲彇鍏变韩鍙橀噺鏃跺彲浠ヨ幏寰楁渶鏂板€肩殑浣跨敤銆?/li>
以上是关于Java 骞跺彂锛氬唴缃攣 Synchronized的主要内容,如果未能解决你的问题,请参考以下文章