线程中的静态同步和非静态同步方法

时间:2011-04-13 19:39:30

标签: java multithreading

任何人都可以解释声明......“静态同步方法和非静态同步方法不会相互阻塞 - 它们可以同时运行”

3 个答案:

答案 0 :(得分:16)

static synchronized void test() { foo(); }

等于

static void test() { synchronized(MyClass.class) { foo(); } }

synchronized void test() { foo(); }

等于

void test() { synchronized(this) { foo(); } }

这意味着:静态方法锁定类的类对象。非静态方法锁定调用它们的实例(默认情况下,synchronized(anyOtherLock)也是可能的)。由于它们锁定不同的物体,因此它们不会相互阻挡。

答案 1 :(得分:9)

静态方法和非静态方法的锁定对象不同。静态方法使用Class对象作为锁(lock obj:MyClass.class),而非静态方法使用实例对象作为锁定,此时方法的调用被绑定到该锁(lock obj: this)。

答案 2 :(得分:0)

非静态同步方法将监视器锁定打开'这意味着只有当前对象被锁定。因此,当前对象关联的所有线程都将被阻止访问该类的非静态同步方法(如果有的话)线程正在访问非静态同步方法。而其他对象的线程仍然可以访问这些方法。

静态同步方法将监视器锁定放在Class对象上 - 这意味着如果任何对象的线程正在访问该方法,则所有线程都将被阻止以访问该类的所有静态同步方法。

公共类TestSync {

public synchronized void n1(int threadId)
{
    snooze(threadId);
    System.out.println("Sync non static n1 " + threadId);
}

public void n2(int threadId)
{ 
    snooze(threadId);
    System.out.println(" non static n2 " + threadId);
}

public static synchronized void s1(int threadId)
{
    snooze(threadId);
    System.out.println("Sync static s1 "+  threadId);
}

public static void s2(int threadId)
{
    snooze(threadId);
    System.out.println(" static s2 "+  threadId);
}

static void snooze(int threadId)
{
    System.out.println("Waiting ... "+ threadId);
    try {
        Thread.sleep(10000);
    } catch (InterruptedException e) {
        e.printStackTrace();
    }
}

public static void main(String[] args) {
    TestSync ob = new TestSync();
    TestSync ob2=new TestSync();
    TestSync ob3=new TestSync();
    TestSync ob4=new TestSync();

    Runnable r1=()-> {
        /*ob.n1(10);
        ob.n2(10);*/
        ob.s1(10);
        //ob.s2(10);
    };

    Runnable r3=()-> {
        /*ob2.n1(30);
        ob2.n2(30);*/
        ob2.s1(30);
        //ob2.s2(30);
    };

    Runnable r4=()-> {
        /*ob3.n1(40);
        ob3.n2(40);*/
        ob3.s1(30);
        //ob3.s2(30);
    };

    Thread t1=new Thread(r1);
    Thread t2= new Thread(r2);
    Thread t3= new Thread(r3);
    Thread t4= new Thread(r4);
    Thread t5= new Thread(r5);
    t1.start();
    t3.start();
    t4.start();

}

} 运行一次以进行静态同步,然后取消注释runnable和run中的非静态同步调用(以及注释静态同步)。你会明白的。