synchronized用static修饰和不用static修饰的区别,synchronized同步代码块this和类的Class对象作为锁的区别。
看下面的例子:
package com.andy.juc; public class SynchronizedTest { public static void main(String[] args) { new Thread(new Runnable() { @Override public void run() { sub(); } }).start(); try { Thread.sleep(1000); } catch (InterruptedException e) { e.printStackTrace(); } SynchronizedTest.add(); } public static synchronized void add(){ System.out.println("hello add"); } public static synchronized void sub() { try { Thread.sleep(5000); } catch (InterruptedException e) { e.printStackTrace(); } System.out.println("hello sub"); } }
一个是实例方法,一个是静态方法
package com.andy.juc; public class SynchronizedTest { public static void main(String[] args) { new Thread(new Runnable() { @Override public void run() { sub(); } }).start(); try { Thread.sleep(1000); } catch (InterruptedException e) { e.printStackTrace(); } new SynchronizedTest().add(); } public synchronized void add(){ System.out.println("hello add"); } public static synchronized void sub() { try { Thread.sleep(5000); } catch (InterruptedException e) { e.printStackTrace(); } System.out.println("hello sub"); } }
创建两个对象,分别调用自己的实例方法,不会有并发问题。
package com.andy.juc; public class SynchronizedTest { public static void main(String[] args) { new Thread(new Runnable() { @Override public void run() { new SynchronizedTest().sub(); } }).start(); try { Thread.sleep(1000); } catch (InterruptedException e) { e.printStackTrace(); } new SynchronizedTest().add(); } public synchronized void add(){ System.out.println("hello add"); } public synchronized void sub() { try { Thread.sleep(5000); } catch (InterruptedException e) { e.printStackTrace(); } System.out.println("hello sub"); } }
同一个对象,锁资源相互排斥
package com.andy.juc; public class SynchronizedTest { public static void main(String[] args) { SynchronizedTest synchronizedTest = new SynchronizedTest(); new Thread(new Runnable() { @Override public void run() { synchronizedTest.sub(); } }).start(); try { Thread.sleep(1000); } catch (InterruptedException e) { e.printStackTrace(); } synchronizedTest.add(); } public synchronized void add(){ System.out.println("hello add"); } public synchronized void sub() { try { Thread.sleep(5000); } catch (InterruptedException e) { e.printStackTrace(); } System.out.println("hello sub"); } }
同步代码块,用类的Class对象来加锁,互斥
package com.andy.juc; public class SynchronizedTest { public static void main(String[] args) { new Thread(new Runnable() { @Override public void run() { new SynchronizedTest().sub(); } }).start(); try { Thread.sleep(1000); } catch (InterruptedException e) { e.printStackTrace(); } new SynchronizedTest().add(); } public void add(){ synchronized(SynchronizedTest.class){ System.out.println("hello add"); } } public void sub() { synchronized(SynchronizedTest.class){ try { Thread.sleep(5000); } catch (InterruptedException e) { e.printStackTrace(); } System.out.println("hello sub"); } } }