4 ms·
A good trick to convince JS engines that you are dealing with integers is to use the "`|0` operator": let a = 1; let b = 2; let c = a+b|0; // c is guaranteed
by yuri91 5y ago
A good trick to convince JS engines that you are dealing with integers is to use the "`|0` operator":
let a = 1;
let b = 2;
let c = a+b|0; // c is guaranteed to be a 32 bit signed integer
This not only ensures correct 32 bit integer semantics (like wrapping around), but also helps the engines to use actual integer instructions in the generated machine code.
For unsigned 32 bit integers, there is `>>>0`, and
for multiplication, there is Math.imul().
- vanderZwan 5y agoOne of my colleagues told me to stop doing that because in (I think) V8 these values are immediately converted back to a double nowadays. So annotating all code with |0 doesn't really add speed benefits there, just extra conversions between doubles and integers. Said colleague used to maintain human-asmjs so I trust he knows what he's talking about. [0] https://github.com/zbjornson/human-asmjs https://github.com/zbjornson/human-asmjs
- cpleppert 5y ago>> This not only ensures correct 32 bit integer semantics (like wrapping around), but also helps the engines to use actual integer instructions in the generated machine code. But there is only one type of number in javascript. Everything is just a double(BigInt aside). You get a 32-bit integer because the bitwise operator casts the result to one. c has the exact same semantics as any other js number. Yeah there are tricks to convince the engine you are using an integral type but those unless you are doing a lot of benchmarks they aren't really useful. Any compilation tier can choose to use any intermediate representation it wants.
- vanderZwan 5y ago> But there is only one type of number in javascript. Everything is just a double(BigInt aside). There is nothing stopping JS engines from trying to infer when a number is only an integer and optimize for that. In fact, that's what Small Integer (SMI) optimizations are all about[0]. It's just that |0 isn't really able to guarantee that our number value is the type of SMI that V8 optimizes for (since the V8 SMIs are 31 bits, and bitmasking operations only guarantee 32 bit integers) https://ponyfoo.com/articles/an-introduction-to-speculative-optimization-in-v8 https://ponyfoo.com/articles/an-introduction-to-speculative-...