基于方法的Java线程同步

基于方法的Java线程同步,java,Java,我尝试使用方法同步运行一个示例线程模块,但结果与预期不符 因为我已经同步了m1(),所以我希望线程1完全打印值0…10,然后线程2开始运行 但是,在这种情况下,数字是交替打印的 package threadexample; public class Test implements Runnable{ public void run(){ m1(); } public synchronized void m1(){ for (int i

我尝试使用方法同步运行一个示例线程模块,但结果与预期不符

因为我已经同步了m1(),所以我希望线程1完全打印值0…10,然后线程2开始运行

但是,在这种情况下,数字是交替打印的

package threadexample;

public class Test implements  Runnable{
    public void run(){
        m1();
    }
    public synchronized void m1(){
        for (int i = 0; i < 10; i ++){
            System.out.println(Thread.currentThread().getName() + " Value of i = " + i);
        }
    }
    Test(String threadname){
        super();
    }

    public static void main(String[] args){
            Test a = new Test("A");
            Test b = new Test("B");
            Thread t1 = new Thread(a);
            Thread t2 = new Thread(b);
            t1.start();
            t2.start();

    }   

}



Output:

Thread-0 Value of i = 0
Thread-1 Value of i = 0
Thread-0 Value of i = 1
Thread-1 Value of i = 1
Thread-0 Value of i = 2
Thread-1 Value of i = 2
Thread-0 Value of i = 3
Thread-1 Value of i = 3
Thread-0 Value of i = 4
Thread-1 Value of i = 4
Thread-0 Value of i = 5
Thread-1 Value of i = 5
Thread-0 Value of i = 6
Thread-1 Value of i = 6
Thread-0 Value of i = 7
Thread-1 Value of i = 7
Thread-0 Value of i = 8
Thread-1 Value of i = 8
Thread-0 Value of i = 9
Thread-1 Value of i = 9
包线程示例;
公共类测试实现可运行{
公开募捐{
m1();
}
公共同步void m1(){
对于(int i=0;i<10;i++){
System.out.println(Thread.currentThread().getName()+“i=“+i”的值);
}
}
测试(字符串threadname){
超级();
}
公共静态void main(字符串[]args){
试验a=新试验(“a”);
试验b=新试验(“b”);
螺纹t1=新螺纹(a);
螺纹t2=新螺纹(b);
t1.start();
t2.start();
}   
}
输出:
线程-0 i=0的值
线程-1 i=0的值
线程-0 i=1的值
线程-1 i=1的值
线程-0 i=2的值
i=2的螺纹-1值
i=3的螺纹-0值
i=3的螺纹-1值
线程-0 i=4的值
i=4的螺纹-1值
i=5的螺纹-0值
i=5的螺纹-1值
i=6的螺纹-0值
i=6的螺纹-1值
i=7的螺纹-0值
i=7的螺纹-1值
线程-0 i=8的值
i=8的螺纹-1值
线程-0 i=9的值
i=9的螺纹-1值

您已经同步了一个实例方法。它将在实例本身上同步。但是,每个
线程
都使用不同的实例,即它们在不同的对象上都是同步的,因此不会相互阻塞

您需要共享您的
测试
实例

Test a = new Test("A");
Thread t1 = new Thread(a);
Thread t2 = new Thread(a);

或者在不同的共享对象上使用
synchronized
。您可以通过将锁对象作为构造函数参数传递或使用静态字段引用来完成此操作。

您已经同步了一个实例方法。它将在实例本身上同步。但是,每个
线程
都使用不同的实例,即它们在不同的对象上都是同步的,因此不会相互阻塞

您需要共享您的
测试
实例

Test a = new Test("A");
Thread t1 = new Thread(a);
Thread t2 = new Thread(a);

或者在不同的共享对象上使用
synchronized
。您可以通过将锁对象作为构造函数参数传递或使用静态字段引用来实现这一点。

方法上的
synchronized
的问题是它锁定了
。在您的案例中,您有两个不同的实例-每个实例都有一个不同的
this
引用。在方法上使用
synchronized
字与执行此操作相同:

public void m1() {
    synchronized(this) {
        // Critical code section here
    }
}
如果要执行所描述的锁定,代码应如下所示:

public class Test implements  Runnable{

    private final static Object lock = new Object();

    public void run(){
        m1();
    }

    public void m1(){
        synchronized(lock) {
           for (int i = 0; i < 10; i ++){
               System.out.println(Thread.currentThread().getName() + " Value of i = " + i);
           }
        }
    }

   Test(String threadname){
        super();
   }

   public static void main(String[] args){
        Test a = new Test("A");
        Test b = new Test("B");
        Thread t1 = new Thread(a);
        Thread t2 = new Thread(b);
        t1.start();
        t2.start();

   }   

}
公共类测试实现可运行{
私有最终静态对象锁=新对象();
公开募捐{
m1();
}
公共空间m1(){
已同步(锁定){
对于(int i=0;i<10;i++){
System.out.println(Thread.currentThread().getName()+“i=“+i”的值);
}
}
}
测试(字符串threadname){
超级();
}
公共静态void main(字符串[]args){
试验a=新试验(“a”);
试验b=新试验(“b”);
螺纹t1=新螺纹(a);
螺纹t2=新螺纹(b);
t1.start();
t2.start();
}   
}

在这种情况下,您在两个实例之间共享锁(因为它是静态的),这样您就可以锁定同一个对象,并按照您希望的方式进行同步。

方法上的
同步的问题在于它锁定了
。在您的案例中,您有两个不同的实例-每个实例都有一个不同的
this
引用。在方法上使用
synchronized
字与执行此操作相同:

public void m1() {
    synchronized(this) {
        // Critical code section here
    }
}
如果要执行所描述的锁定,代码应如下所示:

public class Test implements  Runnable{

    private final static Object lock = new Object();

    public void run(){
        m1();
    }

    public void m1(){
        synchronized(lock) {
           for (int i = 0; i < 10; i ++){
               System.out.println(Thread.currentThread().getName() + " Value of i = " + i);
           }
        }
    }

   Test(String threadname){
        super();
   }

   public static void main(String[] args){
        Test a = new Test("A");
        Test b = new Test("B");
        Thread t1 = new Thread(a);
        Thread t2 = new Thread(b);
        t1.start();
        t2.start();

   }   

}
公共类测试实现可运行{
私有最终静态对象锁=新对象();
公开募捐{
m1();
}
公共空间m1(){
已同步(锁定){
对于(int i=0;i<10;i++){
System.out.println(Thread.currentThread().getName()+“i=“+i”的值);
}
}
}
测试(字符串threadname){
超级();
}
公共静态void main(字符串[]args){
试验a=新试验(“a”);
试验b=新试验(“b”);
螺纹t1=新螺纹(a);
螺纹t2=新螺纹(b);
t1.start();
t2.start();
}   
}
在本例中,您在两个实例之间共享锁(因为它是静态的),这样您就可以锁定同一个对象,并按照您希望的方式进行同步