多個(gè)線程,每個(gè)線程都可以拿到自己指定的鎖,分別獲得鎖之后狰挡,執(zhí)行synchronized方法體的內(nèi)容捂龄。
public class MyThread {
private int num = 0;
/** static */
public synchronized void printNum(String tag){
try {
if(tag.equals("a")){
num = 100;
System.out.println("tag a, set num over!");
Thread.sleep(1000);
} else {
num = 200;
System.out.println("tag b, set num over!");
}
System.out.println("tag " + tag + ", num = " + num);
} catch (InterruptedException e) {
e.printStackTrace();
}
}
public static void main(String[] args) {
//倆個(gè)不同的對(duì)象
final MyThread m1 = new MyThread();
final MyThread m2 = new MyThread();
Thread t1 = new Thread(new Runnable() {
@Override
public void run() {
m1.printNum("a");
}
});
Thread t2 = new Thread(new Runnable() {
@Override
public void run() {
m2.printNum("b");
}
});
t1.start();
t2.start();
}
}
,而代碼的結(jié)果是m1,m2同時(shí)進(jìn)來(lái)唇撬。
總結(jié):一個(gè)對(duì)象一把鎖(也就是說(shuō)它匕,兩個(gè)線程分別是得到m1,m2這兩個(gè)對(duì)象的鎖,他們兩個(gè)沒(méi)有任何關(guān)系)如果說(shuō)有一天當(dāng)前有一個(gè)線程執(zhí)行printNum方法窖认,我就不希望其他的線程進(jìn)來(lái)執(zhí)行豫柬,怎么辦呢?扑浸?
在方法上加static烧给,全局變量加static,表示的是在靜態(tài)的方法上加上synchronized修飾喝噪,那么這個(gè)線程調(diào)用printNum所或得的鎖础嫡,就是class這個(gè)類級(jí)別的鎖,無(wú)論實(shí)例化多少個(gè)對(duì)象,都沒(méi)有任何關(guān)聯(lián)關(guān)系酝惧。也就是說(shuō)t1,t2線程有一個(gè)先后執(zhí)行的順序榴鼎。
關(guān)鍵字synchronized取得的鎖都是對(duì)象鎖,而不是把一段代碼(方法)當(dāng)作鎖晚唇,示例代碼中那個(gè)線程先執(zhí)行synchronized關(guān)鍵字的方法巫财,那個(gè)線程就持有該方法所屬對(duì)象的鎖宋下,(lock),兩個(gè)對(duì)象火诸,線程獲得的就是兩個(gè)不同的鎖,他們互不影響羊娃。
有一種情況則是相同的鎖,即在靜態(tài)方法上加上synchronized關(guān)鍵字闽瓢,表示鎖定.class類接癌,類一級(jí)別的鎖,(獨(dú)占,class類)鸳粉。