parallel-js/parallel.js

Newbie problems...

zaino opened this issue · 12 comments

zaino commented

Hi I'm new to javascript, webworkers, pretty much looking around at everything available, and noticed your library.
I'm running one of your simple examples and failing to understand the flow.

var p = new Parallel([40, 41, 42]);
log = function () 
{ 
  console.log(arguments); 
};
function fib(n) {
    return n < 2 ? 1 : fib(n - 1) + fib(n - 2);
};
p.map(fib).then(log);

let count = 0;
while (count<100000)
  count++;
console.log("Done");

What I don't get, is why are the workers spawned only after the last instruction is done. Looking at the chrome debugger, no thread whatsoever aside from main, starts until the last console.log is done.

I realize this failure is due to my ignorance, but I would nonetheless appreciate some insight.

Cheers.

You need to await your p.map

zaino commented

Thanks @mathiasrw.
I tried this:

async function asyncCall() {
  var p = new Parallel([40, 41, 42]);
  log = function () 
  { 
    console.log(arguments); 
  };
  function fib(n) {
      return n < 2 ? 1 : fib(n - 1) + fib(n - 2);
  };
  //p.map(fib).then(log);
  let res = await p.map(fib);

  console.log(res);
}

asyncCall();

let count = 0;
while (count<1000000000)
  count++;

console.log("Done");

but I get the same behavior. Until the while loop is done, I don't get the results from fib.

Now you have to await asyncCall()

zaino commented

Thanks!
That's the code in my main.js file.
I cannot await asyncCall, I get the error that warns me await can we used only in async methods.
That's the reason why I created asyncCall to begin with.

zaino commented

I also tried going back to basic Worker manually created, but I get the same thing, the Worker thread does not get spawned until the main thread execution ends.

It's probably common knowledge for web developers, but coming from c++ and such, I was expecting the threads to be spawned when the worker has done loading it's own script.

Which is not the case.

I cannot await asyncCall, I get the error that warns me await can we used only in async methods.

I know. Im letting you explore the problem space a bit.

Top level await is not supported. A way of getting around that is to put all of you code into a self invoking function first.


async function something(){
	await xyz
}



(async ()=>{
  await something()

  loop

  console.log('Done')
})()

zaino commented

Ok...I think I’m starting to understand more.
BTW I appreciate greatly you taking the time and letting me figure out with guided hints!
I’ll think about all this and get back to you after I concocted something :)

@zaino All good.

Once upon a time, I gained a lot from watching this: https://www.youtube.com/watch?v=cCOL7MC4Pl0

zaino commented

This then:

(async ()=>{
  var p = new Parallel([40, 41, 42]);
  log = function () 
  { 
    console.log(arguments); 
  };
  function fib(n) {
      return n < 2 ? 1 : fib(n - 1) + fib(n - 2);
  };
  //p.map(fib).then(log);
  let res = await p.map(fib);
  console.log(res);
  
  let count = 0;
  while (count<1000000000)
    count++;

  console.log('Done the parallel map')
})()

console.log("Done");

I will watch the video, thanks a lot!

Here Done will be printed before "Done with parallel"

When you watch the video you will see that it does everything it can until the end. On its way all "await" is put to the side and looked at in the next event loop.

So basically its getting to await p.map(fib);- will return from that function, continue (do the Done part) and after the end is reached it will start p.map

zaino commented

Yes, that's the flow I'm observing. And, again, until we exit the scope of the caller (we print "Done"), none of the workers actually start.

Now I'm going to watch the video you suggested, since I feel I'm missing some basic knowledge on the event loop.

I also wanted to specify why I'm interest in this.
What I wanted to explore, is to see if I can use Parallel.js to turn a for loop into a "parallel" loop.
So I would like to spawn a bunch of workers, wait till they are done, and continue.
Imagine you have a code like this:

main.js:

let results = computeResults(data);

compute.js:

let computeResults = function (data) {
   let results = [];
   for(let i=0; i<data.length; ++i) {
      results.push( doSomething(data[i]));
   }
   return results;
}

I wanted to see if I could use Parallel.map to parallelize that loop.
The problem is that with a pattern similar to what we discussed so far, the actual workers won't start until return results; is executed, returning an empty list.

zaino commented

After watching the video you suggested, I have a much better understanding of what is going on, and I think I’m close to get what I was suggesting above working.
I’m having some issues with .require, but probably I should open a new discussion for that, since it’s not related to what you helped me with here.