Da_Chris
Erfahrenes Mitglied
Hallo Leute ich bin echt am verzweifeln wir sollen für Studium eine Planetensymulation umsetzen. Das ganze soll Thread basierend mit dem Master-Worker-Pattern ablaufen.
Leider schläft mein Programm regelmässig ein und ich bin am Ende meines Lateins. (Ablaufdiagramme ohne Ende gezeichnet, zig sachen versucht etc...)
Master:
Worker:
Tasks:
Und das kommt raus:
ich hoffe das ist nicht zuviel code aber ich steh grad voll auf dem schlauch und brauch dringend Hilfe!
Danke schonmal!
Leider schläft mein Programm regelmässig ein und ich bin am Ende meines Lateins. (Ablaufdiagramme ohne Ende gezeichnet, zig sachen versucht etc...)
Master:
Code:
package planetary_server;
import java.util.ArrayList;
import java.util.List;
public class Master {
private Tasks tasks;
private List<Worker> workerList = new ArrayList<Worker>();
protected Object workerWaitDummy = new Object();
public final double gravConst;
public final double deltaT;
public static final boolean debug = true;
public Master(double deltaT, double gravConst) {
if(Master.debug)
System.err.println("Master()");
this.deltaT = deltaT;
this.gravConst = gravConst;
this.tasks = new Tasks();
this.buildWorker(getNumberOfProcessors());
}
private void buildWorker(int numCores) {
if(Master.debug)
System.err.println("Master.buildWorker()");
for(int i = 0; i<numCores; i++) {
Worker w = new Worker(i,this.tasks, this);
w.start();
this.workerList.add(w);
}
}
public List<Planet> calculate(List<Planet> tasks) {
if(Master.debug)
System.err.println("Master.calculate("+tasks.toString()+")");
this.tasks.setTasks(tasks);
synchronized (this.workerWaitDummy) {
System.err.println("- notifyAll workers");
this.workerWaitDummy.notifyAll();
}
try {
synchronized (this) {
if(!this.tasks.isFinished()) {
System.err.println("- wait master");
this.wait(); }
}
} catch (InterruptedException e) {
e.printStackTrace();
}
List<Planet> results = this.tasks.getResults();
return results;
}
/**
* returns the number of available processors
*
* @return availableProcessors
*/
public static int getNumberOfProcessors() {
if (debug)
System.err.println("master.getNumberOfProcessors");
Runtime runtime = Runtime.getRuntime();
return runtime.availableProcessors();
}
}
Code:
package planetary_server;
public class Worker extends Thread {
public final int id;
private final Tasks tasks;
private final Master master;
public final double gravConst;
public final double deltaT;
public Worker(int id, Tasks tasks, Master master) {
if(Master.debug)
System.err.println("Worker("+id+", "+tasks+")");
this.tasks = tasks;
this.master = master;
this.gravConst = master.gravConst;
this.deltaT = master.deltaT;
this.id = id;
}
@Override
public void run() {
if(Master.debug)
System.err.println("Worker["+this.id+"].run()");
try {
synchronized (this.master.workerWaitDummy) {
this.master.workerWaitDummy.wait();
}
} catch (InterruptedException e) {
e.printStackTrace();
}
while(true) {
Planet task = this.tasks.getTask();
if(task == null) {
if(this.tasks.isFinished())
synchronized (this.master) {
System.err.println("- notify master");
this.master.notify();
}
try {
synchronized (this.master.workerWaitDummy) {
System.err.println("- wait worker");
this.master.workerWaitDummy.wait();
}
} catch (InterruptedException e) {
e.printStackTrace();
}
}
else {
Planet result = this.calculate(task);
this.tasks.setResult(result);
}
}
}
private Planet calculate(Planet task) {
if(Master.debug)
System.err.println("Worker["+this.id+"].calculate("+task+")");
return SolarSunSystem.calclateOnePlanet(task, this.tasks.getPlanetsOld(), this.deltaT, this.gravConst);
}
}
Code:
package planetary_server;
import java.util.ArrayList;
import java.util.Iterator;
import java.util.List;
public class Tasks {
private List<Planet> planetsOld = new ArrayList<Planet>();
private List<Planet> planetsNew = new ArrayList<Planet>();
private Iterator<Planet> tasksIter = this.planetsOld.iterator();;
public Tasks() {
if(Master.debug)
System.err.println("Tasks()");
}
protected void setTasks(List<Planet> tasks) {
if(Master.debug)
System.err.println("Tasks.setTasks("+tasks.toString()+")");
this.planetsOld.clear();
this.planetsNew.clear();
this.planetsOld.addAll(tasks);
this.tasksIter = this.planetsOld.iterator();
}
protected synchronized List<Planet> getResults() {
if(Master.debug)
System.err.println("Tasks.getResults()");
return this.planetsNew;
}
protected synchronized Planet getTask() {
if(Master.debug)
System.err.println("Tasks.getTask()");
if(this.tasksIter.hasNext())
return this.tasksIter.next();
else
return null;
}
protected synchronized void setResult(Planet result) {
if(Master.debug)
System.err.println("Tasks.setResult("+result+")");
this.planetsNew.add(result);
}
protected synchronized boolean isFinished() {
if(Master.debug)
System.err.println("Tasks.isFinished() "+ (this.planetsNew.size()==this.planetsOld.size()?"true":"false"));
return (this.planetsNew.size()==this.planetsOld.size());
}
public synchronized List<Planet> getPlanetsOld() {
if(Master.debug)
System.err.println("Tasks.getPlanetsOld()");
return new ArrayList<Planet>(this.planetsOld);
}
}
Und das kommt raus:
Code:
Step 3 / 8766 complete! 00:01:378
Master.calculate([id:0,name:Sonne,mass:1.99E30,pos:(16.39744466533697, 0.0025068520996454433, 0.0),speed:(0.0030365633197740683, 8.356172005683118E-7, 0.0), id:1,name:Merkur,mass:3.3E23,pos:(5.790769105713596E10, 5.173161802779882E8, 0.0),speed:(-427.58032436200176, 47898.72676009144, 0.0), id:2,name:Venus,mass:4.87E24,pos:(1.0893934757490266E11, 3.7853958015842587E8, 0.0),speed:(-120.81938929272617, 35049.86005257598, 0.0), id:3,name:Erde,mass:5.97E24,pos:(1.4959965401903943E11, 3.218398621968827E8, 0.0),speed:(-64.0705335843337, 29799.95406031698, 0.0), id:4,name:Mars,mass:6.42E23,pos:(2.2793985098675165E11, 2.6179196830871865E8, 0.0),speed:(-27.595044162058734, 24239.989435254887, 0.0), id:5,name:Jupiter,mass:1.9E27,pos:(7.785699872310099E11, 1.405079995730577E8, 0.0),speed:(-2.3646277908104945, 13009.99985768297, 0.0), id:6,name:Saturn,mass:5.68E26,pos:(1.4339999962174197E12, 1.0367999995099406E8, 0.0),speed:(-0.7004778751271509, 9599.99998348214, 0.0), id:7,name:Uranus,mass:8.68E25,pos:(2.8719999990586216E12, 7.34399999956323E7, 0.0),speed:(-0.1743292852883542, 6799.999998534666, 0.0), id:8,name:Neptun,mass:1.02E26,pos:(4.494999999615862E12, 5.864399999908857E7, 0.0),speed:(-0.07113678170395245, 5429.999999694501, 0.0)])
Tasks.setTasks([id:0,name:Sonne,mass:1.99E30,pos:(16.39744466533697, 0.0025068520996454433, 0.0),speed:(0.0030365633197740683, 8.356172005683118E-7, 0.0), id:1,name:Merkur,mass:3.3E23,pos:(5.790769105713596E10, 5.173161802779882E8, 0.0),speed:(-427.58032436200176, 47898.72676009144, 0.0), id:2,name:Venus,mass:4.87E24,pos:(1.0893934757490266E11, 3.7853958015842587E8, 0.0),speed:(-120.81938929272617, 35049.86005257598, 0.0), id:3,name:Erde,mass:5.97E24,pos:(1.4959965401903943E11, 3.218398621968827E8, 0.0),speed:(-64.0705335843337, 29799.95406031698, 0.0), id:4,name:Mars,mass:6.42E23,pos:(2.2793985098675165E11, 2.6179196830871865E8, 0.0),speed:(-27.595044162058734, 24239.989435254887, 0.0), id:5,name:Jupiter,mass:1.9E27,pos:(7.785699872310099E11, 1.405079995730577E8, 0.0),speed:(-2.3646277908104945, 13009.99985768297, 0.0), id:6,name:Saturn,mass:5.68E26,pos:(1.4339999962174197E12, 1.0367999995099406E8, 0.0),speed:(-0.7004778751271509, 9599.99998348214, 0.0), id:7,name:Uranus,mass:8.68E25,pos:(2.8719999990586216E12, 7.34399999956323E7, 0.0),speed:(-0.1743292852883542, 6799.999998534666, 0.0), id:8,name:Neptun,mass:1.02E26,pos:(4.494999999615862E12, 5.864399999908857E7, 0.0),speed:(-0.07113678170395245, 5429.999999694501, 0.0)])
- notifyAll workers
Tasks.isFinished() false
- wait master
- wait worker
ich hoffe das ist nicht zuviel code aber ich steh grad voll auf dem schlauch und brauch dringend Hilfe!
Danke schonmal!