Reputation: 43843
I'm looking at ways to multiply faster in JavaScript, and I found this
which has this text
Instead of multiplying, use the bit shift operation. it looks a little more complex, but once you get the hang of it, it’s pretty simple. The formula to multiply x * y is simply x << (y-1)
As a bonus, everyone else will think you’re really smart!
// multiply by 1
[1,2,3,4].forEach(function(n){ return n<<0; }) // 1,2,3,4
// multiply by 2
[1,2,3,4].forEach(function(n){ return n<<1; }) // 2,4,6,8
// multiply by 3
[1,2,3,4].forEach(function(n){ return n<<2; }) // 3,6,9,12
// etc
However this doesn't seem to work for me. Does anyone know what's wrong?
Thanks
Upvotes: 0
Views: 1582
Reputation: 9
Bit shift is not the same as multiplying by any number. This is how bit shift works in decimal for example:
1234 >> 0 = 1234
1234 >> 1 = 0123 #discards the last digit.
0123 >> 2 = 0001 #discards the last two digit
So in decimal, shifting digits to the right is like integer division by 10. When shifted by two digits it's the same as dividing by 10^2.
Now computers work with binary words. So instead of a digit shift, we have bit shifts.
10101011 >> 1 = 01010101
This is basically dividing by 2^1.
10101011 >> n
is simply dividing by 2^n.
Now in the same manner,
10101011 << n
is multiplying by by 2^n. This adds n zeroes behind the binary word.
Hope it's clearer now :)
Cheers
Upvotes: -2
Reputation: 1996
Incidentally, if you want to know why it isn't working for you, you will want to use map
instead of forEach
since forEach
ignores the return.
So do this instead:
// multiply by 1
[1,2,3,4].map(function(n){ return n<<0; }) // 1,2,3,4
// multiply by 2
[1,2,3,4].map(function(n){ return n<<1; }) // 2,4,6,8
// multiply by 4
[1,2,3,4].map(function(n){ return n<<2; }) // 4,8,12,16
// multiply by 8
[1,2,3,4].map(function(n){ return n<<3; }) // 8, 16, 24, 32
And as others have mentioned - don't use this for multiplication. Just take this as a clarity of forEach vs map...
Upvotes: -2
Reputation:
Ignore that article. It's intended as humor -- the advice it's giving is intentionally terrible and wrong.
Multiplication does not involve "expensive logarithmic look up tables and extremely lucky guesses" with "dozens of guesses per second". It is a highly optimized hardware operation, and any modern CPU can perform hundreds of millions (or more!) of these operations per second.
Bitwise operations are not faster than multiplication in Javascript. In fact, they're much slower -- numbers are generally stored as double-precision floating point by default, so performing a bitwise operation requires them to be converted to integers, then back.
Bit-shifting is not equivalent to multiplication in the way that the article implies. While left-shifting by 0 and 1 are equivalent to multiplication by 1 and 2, the pattern continues with <<2
and <<3
being equivalent to a multiplication by 4 and 8, not 3 and 4.
Array.forEach
does not return a value. The appropriate function to use here would be Array.map
.
The other "Javascript hacks" described in the article are even worse. I won't bother going into details.
Upvotes: 8