關(guān)鍵字synchronized可以應(yīng)用在static靜態(tài)方法上尖昏,代表著對當(dāng)前*.java文件對應(yīng)的Class類進行持鎖仰税。
package other.thread4;
public class Service {
public synchronized static void printA() {
try {
System.out.println("線程:" + Thread.currentThread().getName()
+ "在" + System.currentTimeMillis() + "進入printA");
Thread.sleep(3000);
System.out.println("線程:" + Thread.currentThread().getName()
+ "在" + System.currentTimeMillis() + "離開printA");
} catch (InterruptedException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
public synchronized static void printB() {
System.out.println("線程:" + Thread.currentThread().getName()
+ "在" + System.currentTimeMillis() + "進入printB");
System.out.println("線程:" + Thread.currentThread().getName()
+ "在" + System.currentTimeMillis() + "離開printB");
}
}
public class ThreadA extends Thread {
@Override
public void run() {
Service.printA();
}
}
public class ThreadB extends Thread {
@Override
public void run() {
Service.printB();
}
}
public class Test {
public static void main(String[] args) {
ThreadA threadA = new ThreadA();
threadA.setName("A");
threadA.start();
ThreadB threadB = new ThreadB();
threadB.setName("B");
threadB.start();
}
}
image.png
從運行效果來看,似乎都是同步的效果抽诉,就和將synchronized關(guān)鍵字加到非static方法上使用的效果是一樣的陨簇。其實兩者有著本質(zhì)的不同,synchronized關(guān)鍵字加到static靜態(tài)方法上是給Class類上鎖迹淌,而synchronized關(guān)鍵字加到非static靜態(tài)方法上是給對象上鎖河绽。
驗證
public class Service {
public synchronized static void printA() {
try {
System.out.println("線程:" + Thread.currentThread().getName()
+ "在" + System.currentTimeMillis() + "進入printA");
Thread.sleep(1000);
System.out.println("線程:" + Thread.currentThread().getName()
+ "在" + System.currentTimeMillis() + "離開printA");
} catch (InterruptedException e) {
e.printStackTrace();
}
}
public synchronized void printB() {
System.out.println("線程:" + Thread.currentThread().getName()
+ "在" + System.currentTimeMillis() + "進入printB");
System.out.println("線程:" + Thread.currentThread().getName()
+ "在" + System.currentTimeMillis() + "離開printB");
}
}
public class ThreadA extends Thread {
private Service service;
public ThreadA(Service service) {
this.service = service;
}
@Override
public void run() {
service.printA();
}
}
public class ThreadB extends Thread {
private Service service;
public ThreadB(Service service) {
this.service = service;
}
@Override
public void run() {
service.printB();
}
}
public class Test {
public static void main(String[] args) {
Service service = new Service();
ThreadA threadA = new ThreadA(service);
threadA.setName("A");
threadA.start();
ThreadB threadB = new ThreadB(service);
threadB.setName("B");
threadB.start();
}
}

###異步的原因是持有不同的鎖,一個是對象鎖唉窃,另外一個是Class鎖耙饰,而Class鎖可以對類的所有對象實例起作用。
public class Service {
public synchronized static void printA() {
try {
System.out.println("線程:" + Thread.currentThread().getName()
+ "在" + System.currentTimeMillis() + "進入printA");
Thread.sleep(1000);
System.out.println("線程:" + Thread.currentThread().getName()
+ "在" + System.currentTimeMillis() + "離開printA");
} catch (InterruptedException e) {
e.printStackTrace();
}
}
public synchronized static void printB() {
System.out.println("線程:" + Thread.currentThread().getName()
+ "在" + System.currentTimeMillis() + "進入printB");
System.out.println("線程:" + Thread.currentThread().getName()
+ "在" + System.currentTimeMillis() + "離開printB");
}
}
package other.thread4;
public class ThreadA extends Thread {
private Service service;
public ThreadA(Service service) {
this.service = service;
}
@Override
public void run() {
service.printA();
}
}
package other.thread4;
public class ThreadB extends Thread {
private Service service;
public ThreadB(Service service) {
this.service = service;
}
@Override
public void run() {
service.printB();
}
}
public class Test {
public static void main(String[] args) {
Service service = new Service();
ThreadA threadA = new ThreadA(service);
threadA.setName("A");
threadA.start();
Service service2 = new Service();
ThreadB threadB = new ThreadB(service2);
threadB.setName("B");
threadB.start();
}
}

同步synchronized(class)代碼塊的作用其實和synchronized static方法的作用一樣纹份。