在 java 中跨 类 同步

synchronized across classes in java

我同时有两个线程运行,一个主线程,和一个class旧的布尔变量,我目前有一个线程打印赔率,另一个打印偶数,但我我让他们互相等待,以便按顺序打印 1 - 100。

我目前正在我的 NumberPrinter class 中引用一个布尔对象,我正在使用它使一个线程进入等待状态以等待另一个线程。我知道如何在同一个 class 中进行同步,但是当我尝试跨线程进行同步时,它只是挂起并且看起来布尔变量没有被更新或与两个线程同步。至少这就是我认为问题所在的原因

感谢任何建议

我的测试class

public class Test {

    public static void main(String[] args) throws InterruptedException {

        NumberPrinter np = new NumberPrinter();
        single ent = new single(np);// new state
        Double ont = new Double(np);// new state


        ent.start();
        ont.start();


    }

}

class偶数

public class single extends Thread {

    private NumberPrinter printer;

    public single(NumberPrinter np) {
        this.printer = np;
    }

    public synchronized void run() {
        try {

            for (int i = 1; i <= 100; i++) {
                System.out.println(printer.isOdd);
                if (i % 2 == 0) {
                    if (printer.isOdd == true) {
                        wait();
                    }
                    System.out.println(i);
                    printer.isOdd = true;
                    notifyAll();
                }
            }
        } catch (InterruptedException e) {
            // TODO Auto-generated catch block
            e.printStackTrace();
        }
    }

}

class 为奇数

public class Double extends Thread {

    private NumberPrinter printer;
    public Double(NumberPrinter np) {
        this.printer = np;
    }


    public synchronized void run() {
        try {
            for (int i = 1; i <= 100; i++) {
                System.out.println(printer.isOdd);
                if (i % 2 == 1) {
                    if (printer.isOdd == false) {
                        wait();
                    }
                    System.out.println(getName() + ": " + i);
                    printer.isOdd = false;
                    notifyAll();
                }
            }
        } catch (InterruptedException e) {
            // TODO Auto-generated catch block
            e.printStackTrace();
        }
    }

}

a class 保存布尔变量

package single;

public class NumberPrinter {

    public boolean isOdd = true;

}

waitnotifyAll 需要从两个线程对同一个对象调用。您还需要在该对象上进行同步。您正在使用线程实例,但有两个不同的实例。您可以为此使用 printer 对象,或者您可以创建一个 new Object() 并使用它。 wait 也应该在 while 循环中使用而不是 if 语句。

public void run() {
    try {
        for (int i = 1; i <= 100; i++) {
            synchronized(printer) {
                System.out.println(printer.isOdd);
                if (i % 2 == 1) {
                    while (printer.isOdd == false) {
                        printer.wait();
                    }
                    System.out.println(getName() + ": " + i);
                    printer.isOdd = false;
                    printer.notifyAll();
                }
            }
        }
    } catch (InterruptedException e) {
        // TODO Auto-generated catch block
        e.printStackTrace();
    }
}