简体   繁体   中英

Would it be faster to iterate over a giant array in parallel or synchronously?

Given a giant array and a single core machine, would it be faster to iterate over the array in parallel or sequentially? Assume no work is being done as part of the iteration, it's literally just iterating over the array.

My gut says it would be faster to do sequentially, but I can't justify the answer with my knowledge of OSes and processors. It seems like the same amount of work must be done either way, but parallel execution would incur extra complexity for context switches.

The real world extension of this question is javascript's forEach method. Native forEach executes its callbacks synchronously

var a = [1,2,3,4,5,6...100000000000000];
a.foreach(function(number) {
    // do computationally expensive, synchronous operation eg lots of additions/multiplications
});
console.log('done iterating through for loop and doing all of the work')

Would it ever be advantageous to use an asynchronous version of forEach for the above code (especially given that js can only utilize a single core)?

If we do the same problem but with asynchronous work, the forEach callbacks will become asynchronous as soon as the blocking operation occurs.

var a = [1,2,3,4,5,6...100000000000000];
a.foreach(function(number) {
    // do asynchronous work, eg access to filesystem
    $.ajax({
        url: 'http://google.com',
        success: function() {
            console.log('suceeded for ' + number)
        })
});
console.log('done iterating through for loop but not with all async operations')

In this case, would it ever be advantageous to use an async version of forEach? It seems like we're already taking better advantage of the CPU in the synchronous version by only switching for IO instead of switching before we even initiate the io.

So long as you're using a single core, there is NO advantage, ever, to doing some kind of parallel operations. You are correct that setting up multiple tasks/threads incurs a certain amount of overhead on each of them. And time-sharing the single core across the parallel ops incurs an overhead on each task switch. Iterating sequentially has no such overhead. The only time you have an advantage to parallel ops is when you have multiple cores.

Modern CPUs are all pipelined and most of them are superscalar to boot. But attempting some kind of parallel ops isn't going to "pack the pipeline" or fill the superscalar units. I don't know that any Javascript engines out there can do that.

Oh, and just for the record, you'd be better off with a for loop than a foreach. The simple reason is that foreach has to call a function on each pass, even if it's an anonymous function. Calling a function incurs a certain amount of overhead. A for loop, where the contents of the function are inlined into the body of the loop, will have no such overhead. This has been widely debated in other fora but my own experience bears out this fact.

It completely depends on the code (glad you have provided that). So the answer to your first question would be No . And for second question It depends .

If the code is full CPU bound in a single core machine synchronous version will be a little bit faster. If there is any IO bound code asynchronous version will be faster on the same machine. Because accessing IO doesn't deal with CPU.

Only on a multi core machine, cpu bound code will run faster if they run in asynchronous mode. IO bound code will still run faster than its synchronous sister.

Here is a summery table,

type                                  cpu bound   io bound   mixed
-------------------------------------------------------------------
single-core synchronous               normal      slower     slower
single-core asynchronous              normal      faster     faster
multi-core synchronous                normal      slower     slower
multi-core asynchronous               faster      faster     faster

Notes:

  1. Its assumed that all the code that runs on a single iteration is not dependent to each other.
  2. In most of the real-life use cases the code we want to parallelize is a mix of IO and CPU.
  3. Its very hard to separate IO bound & CPU bound part

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM