@pshevnin

Почему поток не останавливается?

Добрый день, подскажите почему потоки бегут бесконечно, хотя по идее, должны останавливаться
import java.util.Random;

class Vlakno extends Thread {
    private String name;
    boolean isRun;
    boolean isWait;

    public Vlakno(String name){
        this.name = name;
        isRun = true;
        isWait = false;
        start();

    }

    public void run() {
        int counter = 1;
        while (isRun){

            System.out.println(name + " - " + counter++);
        }
    }
}

public class ZK3 {
    public static void main(String[] args) throws InterruptedException {
        Vlakno liche = new Vlakno("liche");
        Vlakno sude = new Vlakno("sude");
        Random random = new Random();
        for (int i = 0; i < 10; i++) {

            int rnd = random.nextInt(10);
            if (rnd % 2 == 0){
                if (sude.isWait){
                    synchronized (sude){
                        sude.isWait = false;
                        sude.notify();
                    }
                }
                else{
                    synchronized (sude){
                        sude.isWait = true;
                        sude.wait();
                    }
                }

            }
            else{
                if (liche.isWait){
                    synchronized (liche){
                        liche.isWait = false;
                        liche.notify();
                    }
                }
                else{
                    synchronized (liche){
                        liche.isWait = true;
                        liche.wait();
                    }
                }

            }
        }
        synchronized (sude){
            sude.isRun = false;
        }
        synchronized (liche){
            liche.isRun = false;
        }
        
    }
}
  • Вопрос задан
  • 117 просмотров
Решения вопроса 1
Vamp
@Vamp
Тут есть две проблемы.

Первая очевидная проблема в том, что main поток на первой же итерации впадает в сон на методе wait(), а в программе больше нет потоков, которые могли бы вызвать notify() и разбудить main. Поэтому main бесконечно ждёт и не может остановить liche и sude.

Вторая совсем неочевидная в том, что синхронизация некорректно используется. У вас синхронизируется только запись в переменную isRun. Чтение этой переменной так же должно быть синхронизировано. Иначе это приведет к странным неуловимым багам.
Ответ написан
Пригласить эксперта
Ответы на вопрос 1
sergey-gornostaev
@sergey-gornostaev Куратор тега Java
Седой и строгий
Потому что переменная isRun не волатильная и синхронизация в читающем потоке не выполняется, так что с его точки зрения переменная значения не меняла.
Ответ написан
Комментировать
Ваш ответ на вопрос

Войдите, чтобы написать ответ

Войти через центр авторизации
Похожие вопросы
Bell Integrator Ульяновск
До 400 000 ₽
Bell Integrator Хабаровск
До 400 000 ₽
Bell Integrator Ижевск
До 400 000 ₽
18 апр. 2024, в 01:12
150000 руб./за проект
18 апр. 2024, в 00:10
50000 руб./за проект