为什么Java同步没有按预期工作?

为什么Java同步没有按预期工作?,java,multithreading,synchronized,Java,Multithreading,Synchronized,我试图弄清楚同步方法是如何工作的。根据我的理解,我创建了两个线程T1和T2,它们将调用相同的方法addNew,因为该方法是同步的,它不应该对一个线程和另一个线程执行for循环的所有迭代吗?输出不断变化,有时打印正确,有时打印T1值与T2值的混合值。代码很简单,有人能指出我做错了什么吗?多谢各位 public class Main { public static void main(String[] args) { Thread t1 = new Thread(new A(

我试图弄清楚同步方法是如何工作的。根据我的理解,我创建了两个线程T1T2,它们将调用相同的方法
addNew
,因为该方法是同步的,它不应该对一个线程和另一个线程执行for循环的所有迭代吗?输出不断变化,有时打印正确,有时打印T1值与T2值的混合值。代码很简单,有人能指出我做错了什么吗?多谢各位

public class Main {
    public static void main(String[] args) {
        Thread t1 = new Thread(new A());
        Thread t2 = new Thread(new A());
        t1.setName("T1");
        t2.setName("T2");
        t1.start();
        t2.start();
    }
}

public class B {
    public synchronized void addNew(int i){
        Thread t = Thread.currentThread();
        for (int j = 0; j < 5; j++) {
            System.out.println(t.getName() +"-"+(j+i));
        }
    }
}

public class A extends Thread {
    private B b1 = new B();

    @Override
    public void run() {
        b1.addNew(100);
    }
}
公共类主{
公共静态void main(字符串[]args){
线程t1=新线程(新A());
线程t2=新线程(新A());
t1.集合名(“t1”);
t2.设定名称(“t2”);
t1.start();
t2.start();
}
}
公共B级{
公共同步的void addNew(int i){
Thread t=Thread.currentThread();
对于(int j=0;j<5;j++){
System.out.println(t.getName()+“-”+(j+i));
}
}
}
公共类A扩展线程{
私有B b1=新B();
@凌驾
公开募捐{
b1.新增(100);
}
}

每个
A
实例都有自己的
B
实例。方法
addNew
B
的一个实例方法。因此,在调用
addNew
期间隐式获取的锁就是接收方
B
实例上的锁。每个线程在不同的
B
上调用
addNew
,从而锁定不同的锁


如果希望所有
B
实例使用公共锁,请创建一个共享锁,并在
addNew
的主体中获取它,这两个
a
对象都有自己的
B
对象。您需要他们共享a
B
,以便同步可以产生效果。

尝试以下方法:

public class Main {
    public static void main(String[] args) {
        A a = new A();
        Thread t1 = new Thread(a);
        Thread t2 = new Thread(a);
        t1.setName("T1");
        t2.setName("T2");
        t1.start();
        t2.start();
    }
}

 class B {
    public synchronized void addNew(int i){
        Thread t = Thread.currentThread();
        for (int j = 0; j < 5; j++) {
            System.out.println(t.getName() +"-"+(j+i));
        }
    }
}

 class A extends Thread {
    private B b1 = new B();

    @Override
    public void run() {
        b1.addNew(100);
    }
}
公共类主{
公共静态void main(字符串[]args){
A=新的A();
螺纹t1=新螺纹(a);
螺纹t2=新螺纹(a);
t1.集合名(“t1”);
t2.设定名称(“t2”);
t1.start();
t2.start();
}
}
B类{
公共同步的void addNew(int i){
Thread t=Thread.currentThread();
对于(int j=0;j<5;j++){
System.out.println(t.getName()+“-”+(j+i));
}
}
}
A类扩展线程{
私有B b1=新B();
@凌驾
公开募捐{
b1.新增(100);
}
}

您与
B
A
的不同实例同步,这两个实例都扩展了
线程
,并传递给
线程
构造函数。这不应该。不要扩展
线程
,扩展
可运行
。谢谢,我如何创建单个共享锁?每个对象都可以充当锁,所以只需创建一个在
B
的所有实例中共享的锁即可
private static final Object lock=new Object()?另外,这将如何改变执行?请解释。对于同步,线程需要锁定对象才能完全执行。当它完成同步代码的执行时,它会离开对象,然后同一个对象被另一个线程锁定并执行,从而实现同步。为了实现这一点,在创建线程对象时,必须将同一个对象作为参数传递。文章作者使用“newa()”创建线程对象,因为arguemnet正在传递两个不同的对象。因此无法实现同步。抱歉,我不清楚。我想让你把它添加到你的帖子中:)