JavaScript WebWorkerPool
Beim eigentlichen WebWorker muss man nur das Antwort-Format einhalten:
{
result:{...},
index:0
}
Index ist der Index des Workloads und wurde in event.data.index übergeben wären der eigentliche Workload in event.data.workload zu finden
ist.
function WebWorkerPool(){
this.workerScript = "";
this.workerData = []; // {msg:{},callback:function}
this.callback = null; //global callback for workerData
this.finishCallback = null;
this.finishCounter=0;
this.worker = null;
this.workers = [];
this.callbackWrapper=function(controller){
return function(event){
controller.finishCounter--;
if(event.data.index && controller.workerData[event.data.index].callback){
controller.workerData[event.data.index].callback(event.data.result);
}
else if(controller.callback){
controller.callback(event.data.result);
}
if(controller.finishCounter == 0){
controller.finishCallback();
try{
controller.worker.close();
for(var iW=0;iW < controller.workers.length; iW++){
controller.workers[iW].close();
}
}
catch(e){
}
}
};
};
this.startSerial = function(){
this.startParallel(1);
};
this.startParallel = function(max){
if(!max){
max = 4;
}
this.finishCounter = this.workerData.length;
this.worker = new Worker(this.workerScript);
for(var iW=0; iW<max; iW++){
var worker = new Worker(this.workerScript);
worker.addEventListener('message', this.callbackWrapper(this), false);
this.workers.push(worker);
}
var factor = this.workerData.length / max;
for(var i=0;i<this.workerData.length;i++){
var workerIndex = Math.floor(i/factor);
this.workers[workerIndex].postMessage(
{
workload: this.workerData.msg,
index:i
});
}
};
}
man kann theoretisch jedem Workload eine eigene Callback-Function mit geben. Wobei eine allgemeine für alle wohl meistens reichen wird.
Wenn alle Workloads abgearbeitet sind wird die finale Callback-Function aufgerufen, um die Ergebnisse weiter zu verarbeiten.