gpt4 book ai didi

Java信号量与指定线程的增量计数

转载 作者:行者123 更新时间:2023-12-01 09:29:48 26 4
gpt4 key购买 nike

有谁知道为什么在编译这段代码后,(我认为)一个线程仍在等待某些东西?我想一个接一个地增加 id 为 10,11 和 12 的线程的计数,直到 50。最后,它起作用了,但是红色按钮(终止)仍然是红色的,这意味着程序仍在运行,并且可能在等待某些东西。

我认为当计数为 50 时,返回应该起作用并从方法中退出。也许可以,但还不够。

代码如下:

public class App12 {

Semaphore sem1 = new Semaphore(1);
Semaphore sem2 = new Semaphore(0);
Semaphore sem3 = new Semaphore(0);

int count = 0;

public void inc() throws InterruptedException {

while (true) {
if (Thread.currentThread().getId() == 10) {
sem1.acquire();
if (count != 50) {
count++;
System.out.println("Thread" + Thread.currentThread().getId() + " has incremented " + count);

sem2.release();
} else
return;
}

if (Thread.currentThread().getId() == 11) {
sem2.acquire();
if (count != 50) {
count++;
System.out.println("Thread" + Thread.currentThread().getId() + " has incremented " + count);

sem3.release();
} else
return;

}

if (Thread.currentThread().getId() == 12) {
sem3.acquire();
if (count != 50) {
count++;
System.out.println("Thread" + Thread.currentThread().getId() + " has incremented " + count);

sem1.release();
} else
return;

}
}
}

public static void main(String[] args) {

App12 ap = new App12();
for (int i = 0; i < 3; i++) {
Thread th1 = new Thread(new Runnable() {
public void run() {
try {
ap.inc();
// dec3();

} catch (InterruptedException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}

}
});
th1.start();

}
}
}

最佳答案

你的问题是你永远不会释放线程上的锁,它们最终会永远等待。

从你的逻辑来看,线程A释放B释放C。

但是,一旦达到 50,线程 A 就会返回。从不释放线程 B 和 C。

因此,您需要的是释放所有其他等待线程的退出条件。

例如(在 while 循环中):

if(count == 50) {
sem2.release();
sem3.release();
sem1.release();
}

问题是,一旦 11 或 12 递增,它们立即再次进入循环,此时它们锁定等待释放的信号量。但是,如果您的计数为 50,则释放该计数的线程将返回,而无需输入您的 if 条件。

或者,您应该能够在 else 子句上添加释放,以便释放所有线程。

希望有帮助,

阿图尔

编辑:这是已实现修复的完整代码:

public class App12 {

Semaphore sem1 = new Semaphore(1);
Semaphore sem2 = new Semaphore(0);
Semaphore sem3 = new Semaphore(0);

int count = 0;

public void inc() throws InterruptedException {

while (true) {

if (Thread.currentThread().getId() == 10) {
sem1.acquire();
if (count != 50) {
count++;
System.out.println("Thread " + Thread.currentThread().getId() + " has incremented " + count);
sem2.release();
} else {
sem2.release();
return;
}
}

if (Thread.currentThread().getId() == 11) {
sem2.acquire();
if (count != 50) {
count++;
System.out.println("Thread " + Thread.currentThread().getId() + " has incremented " + count);
sem3.release();
} else {
sem3.release();
return;
}

}

if (Thread.currentThread().getId() == 12) {
sem3.acquire();
if (count != 50) {
count++;
System.out.println("Thread " + Thread.currentThread().getId() + " has incremented " + count);
sem1.release();
} else {
sem1.release();
return;
}
}

}
}

public static void main(String[] args) {

App12 ap = new App12();
for (int i = 0; i < 3; i++) {
Thread th1 = new Thread(new Runnable() {
public void run() {
try {
ap.inc();
// dec3();
System.out.println("Exist ");
} catch (InterruptedException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}

}
});
th1.start();
}
}
}

注意:一旦计数达到 50,我就会释放信号量,以便其他线程可以退出。

关于Java信号量与指定线程的增量计数,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/39529047/

26 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com