我有一些小问题。 我有一些类处理器和进程。 流程类只有名称和值 处理器必须计算此值并显示它。反过来,处理器实现Runnable接口 但我遇到了麻烦。当我将进程设置为我的处理器时,它开始计算值,但我想启动具有不同进程值的另一个线程,并且此值也设置为第一个线程。 这是代码
package ua.edu.lp.controller;
import java.util.Random;
import ua.edu.lp.controller.processors.FirstProcessor;
import ua.edu.lp.controller.processors.MyBaseProcessor;
import ua.edu.lp.model.MyProcess;
import ua.edu.lp.model.Queue;
public class Computer {
private Queue<MyProcess> queue;
public void run() {
MyBaseProcessor myBaseProcessor = new FirstProcessor();
generateQueue();
for (int i = 0; i < queue.getQueue().size(); i++) {
MyProcess process = queue.get(i);
myBaseProcessor.setProcess(process);
Thread thread = new Thread(myBaseProcessor);
thread.start();
}
}
private void generateQueue() {
queue = new Queue<MyProcess>();
for (int i = 0; i < 10; i++) {
String name = "Process[" + (i + 1) + "]";
MyProcess myProcess = new MyProcess(name,
new Random().nextInt(10) + 1);
queue.add(myProcess);
System.out.println(myProcess.getName() + "\t"
+ myProcess.getValue());
}
}
}
BaseProcessor
package ua.edu.lp.controller.processors;
import ua.edu.lp.model.MyProcess;
public abstract class MyBaseProcessor implements Runnable {
protected MyProcess myProcess;
@Override
public void run() {
synchronized (myProcess) {
calculateValue();
}
}
protected abstract void calculateValue();
public synchronized MyProcess getProcess() {
return myProcess;
}
public synchronized void setProcess(MyProcess myProcess) {
synchronized (myProcess) {
this.myProcess = myProcess;
}
}
}
和FirstProcessor
package ua.edu.lp.controller.processors;
public class FirstProcessor extends MyBaseProcessor {
@Override
protected synchronized void calculateValue() {
System.out.println("First processor is working...");
int value = this.myProcess.getValue();
int result = (int) Math.pow(value, 2);
System.out.println("Pow of " + value + " = " + result);
System.out.println("First processor is free");
}
}
下载所有项目
答案 0 :(得分:1)
这是巨大的代码....只需要编写代码....
对于java中的同步....你可以看看..
Synchronization in java
答案 1 :(得分:1)
您的所有任务都是独立的,因此您不需要在任何地方进行同步。但是,你正在共享一个BaseProcessor对象,该对象在同步时,在处理的生命周期内不会同步。
您只需要同步处理共享数据,其中一个线程可以在线程启动后修改该数据。
BTW:我会使用ExecutorService,因为它将队列和线程池包装在一个类中。
我假设您的队列是线程安全的,因为并非所有队列都是Java。如果不是,那可能是个问题。
这个程序做同样的事情,但它的简单和线程安全。
ExecutorService service = Executors.newSingleThreadExecutor();
Random random = new Random();
for (int i = 0; i < 10; i++) {
final String name = "Process[" + (i + 1) + "]";
final int value = random.nextInt(10) + 1;
service.execute(new Runnable() {
@Override
public void run() {
System.out.println("First processor is working...");
int result = (int) Math.pow(value, 2);
System.out.println("Pow of " + value + " = " + result);
System.out.println("First processor is free");
}
});
System.out.println(name + "\t" + value);
}
service.shutdown();
答案 2 :(得分:1)
使处理器无状态 - 删除字段进程并执行以下操作:
final Processor processor = new Processor();
processor.process(new Process(...));
public void process( final Process process ) {
new Thread(new Runnable() {
//do somethig with process
}).run();
}
注意:处理器必须只执行常见任务 - 运行流程,处理实现业务逻辑,只处理您已完成的计算。
答案 3 :(得分:1)
synchronized(myProcess)
只会为myProcess对象设置MUTEX。只有当两个对象都指向同一个myProcess对象时,不同MyBaseProcessor对象之间的同步才会起作用。
我不知道具体要求是什么,但看起来对我来说是正确的=&gt;一个处理器只能处理一个进程吗?
对我来说有点困惑的是你为什么要在setterMethod setProcess(..)中与目标字段同步。这没有任何效果。
也许您不明白同步将使用对象而不是类型?
BR - 迈克尔