gpt4 book ai didi

java - 使用 3 个线程的多线程 Java

转载 作者:行者123 更新时间:2023-11-30 10:16:39 24 4
gpt4 key购买 nike

我正在尝试创建一个使用线程的程序:线程 1 将整数放入列表中,线程 2 将偶数过滤到偶数列表中,线程 3 对奇数执行相同的操作。

public class Manage {

private Object lock = new Object();
private LinkedList<Integer> intStorage = new LinkedList<Integer>();
private LinkedList<Integer> evens = new LinkedList<>();
private LinkedList<Integer> odds = new LinkedList<>();

public void intCollection() throws InterruptedException {

for (int i = 0; i <= 20; i++) {

synchronized(lock) {

while(i == 20) {
lock.wait();
}

intStorage.add(i);
lock.notifyAll();
System.out.println(intStorage);
}
Thread.sleep(100);
}
}

public void evens() throws InterruptedException {

for(int i = 0; i < intStorage.size() ; i++) {

synchronized(lock) {

if(intStorage.get(i) % 2 != 0) {
lock.wait();
}

if(intStorage.get(i) % 2 == 0) {
int j = intStorage.remove(i);
evens.add(j);
lock.notifyAll();
}
System.out.println(evens);
}
Thread.sleep(1000);
}

}

public void odds() throws InterruptedException {

for(int i = 0; i < intStorage.size() ; i++) {

synchronized(lock) {

if(intStorage.get(i) % 2 == 0) {
lock.wait();
}

if(intStorage.get(i) % 2 != 0) {
int j = intStorage.remove(i);
odds.add(j);
lock.notifyAll();
}
System.out.println(odds);
}
Thread.sleep(1000);
}

}

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

Manager m = new Manager();

Thread t1 = new Thread(){
public void run() {
try {
m.intCollection();
} catch (InterruptedException e) {
}
}
};

Thread t2 = new Thread(){
public void run() {
try {
m.evens();
} catch (InterruptedException e) {
}
}
};
Thread t3 = new Thread(){
public void run() {
try {
m.odds();
} catch (InterruptedException e) {
}
}
};

t1.start();
t2.start();
t3.start();

t1.join();
t2.join();
t3.join();

}
}

线程 1 运行,但是我无法让线程 2 和线程 3 来过滤赔率和偶数。程序在线程 1 完成后终止。

最佳答案

这里的问题是您有三个线程竞争一个锁,但您需要 intCollection 线程首先赢得锁。如果任何其他线程首先赢得锁,您将由于该段而获得越界异常:

for(int i = 0; i < intStorage.size() ; i++) {

synchronized(lock) {

if(intStorage.get(i) % 2 == 0) {

即使 intStorage 为空,它也会调用 get(0) 并产生越界异常。

您也不需要通知和等待调用。我在我的解决方案中删除了那些。我添加了一个检查以查看 intStorage 是否为空,仅此而已。

完整答案如下:

import java.util.*;

public class Manager {

private Object lock = new Object();
private boolean running = true;
private LinkedList<Integer> intStorage = new LinkedList<Integer>();
private LinkedList<Integer> evens = new LinkedList<>();
private LinkedList<Integer> odds = new LinkedList<>();

public void intCollection() throws InterruptedException {

for (int i = 0; i <= 20; i++) {

synchronized(lock) {
intStorage.add(i);
System.out.println("storage: " + intStorage);
}
Thread.sleep(100);
}
running = false;
}

public void evens() throws InterruptedException {

while( (!intStorage.isEmpty()) || running ) {
synchronized (lock) {
if(!intStorage.isEmpty()) {
if (intStorage.get(0) % 2 == 0) {
int j = intStorage.remove(0);
evens.add(j);
}
System.out.println("evens: " + evens);
}
}
Thread.sleep(1);
}

}

public void odds() throws InterruptedException {

while( (!intStorage.isEmpty()) || running ) {
synchronized (lock) {
if(!intStorage.isEmpty()) {
if (intStorage.get(0) % 2 != 0) {
int j = intStorage.remove(0);
odds.add(j);
}
System.out.println("odds: " + odds);
}
}
Thread.sleep(1);
}

}

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

//must be final to access
final Manager m = new Manager();

Thread t1 = new Thread(){
public void run() {
try {
m.intCollection();
} catch (InterruptedException e) {
}
}
};

Thread t2 = new Thread(){
public void run() {
try {
m.evens();
} catch (InterruptedException e) {
}
}
};
Thread t3 = new Thread(){
public void run() {
try {
m.odds();
} catch (InterruptedException e) {
}
}
};

t1.start();
t2.start();
t3.start();

t1.join();
t2.join();
t3.join();

}
}

关于java - 使用 3 个线程的多线程 Java,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/49959345/

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