java - 为什么synchronized不能同步线程?

标签 java multithreading synchronized

我已经设置了标志的值,但结果不是“add”和“sub”交替。为什么?当我查看结果时,它执行了两次“sub”方法。但是当'sub'方法结束时,标志的值将被设置为'false'。但结果却连续打印了两次“subxxxxx”。

class Resource {
    private boolean flag = true;
    private int num = 0;

// At here I have declared an add()
    public synchronized void add() throws InterruptedException {
        if (this.flag == false) {
            super.wait();
        }
        Thread.sleep(100);
        this.num++;
        System.out.println("addition:"+Thread.currentThread().getName() + this.num);
        this.flag = false;
        super.notifyAll();
    }

// At here I have declared an sub()
    public synchronized void sub() throws InterruptedException {
        if (this.flag == true) {
            super.wait();
        }
        Thread.sleep(200);
        this.num--;
        System.out.println("subtraction:"+Thread.currentThread().getName() + this.num);
        this.flag = true;
        super.notifyAll();
    }
}

/*
* I will test it with multiple threads. For example:
*new Thread(ad, "add").start();
*new Thread(ad, "add").start();
*new Thread(sub, "sub").start();
*new Thread(sub, "sub").start();
*When threads start. it will execute alternately. For example:
Thread add:0
Thread sub:-1
Thread add:0
Thread sub:-1
Thread add:0
Thread sub:-1
Thread add:0
Thread sub:-1
But the result is like this:
Thread add:0
Thread sub:-1
Thread sub:-2
Thread add:-1
Thread sub:-3
Thread sub:-4
Why?Why?Why?
*/
        new Thread(ad, "add").start();
        new Thread(ad, "add").start();
        new Thread(sub, "sub").start();
        new Thread(sub, "sub").start();
    }
}

最佳答案

您似乎假设当您的 wait() 调用完成时,flag 已更改为您在调用 wait() 之前想要的内容。没有这样的保证,特别是因为涉及两个以上的线程。您应该检查是否需要继续等待。另请参阅Wait until boolean value changes it state

但总的来说,这些构造的级别太低而无法使用(除非您想了解本质),您应该查看并发 utils 包以获取更简单的更高级别的构造(例如队列、锁存器、条件) .

关于java - 为什么synchronized不能同步线程?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/59915695/

相关文章:

java - 如何在android中的插槽类型中获取时间

linux - 使用 Bash 脚本进行多线程编程

android - AsyncTasks 中的同步方法

java - 不同的线程,访问相同的同步方法,返回意外结果

java - 使用 Java future 进行无限操作是错误的吗?

Java,检查PATH环境中是否存在可执行文件

c# - 通过多个 TransformBlock 进行并行哈希计算会导致困惑

c# - 何时应处置 ManualResetEvent?

java - getter 和 setter 应该同步吗?

java - 什么是NullPointerException,我该如何解决?