1269
votes

I'd like to convert a float to a whole number in JavaScript. Actually, I'd like to know how to do BOTH of the standard conversions: by truncating and by rounding. And efficiently, not via converting to a string and parsing.

10
If you didn't know it, all numbers in javascript are floats. From the specification:some
4.3.20 Number Type: The type Number is a set of values representing numbers. In ECMAScript, the set of values represents the doubleprecision 64-bit format IEEE 754 values including the special “Not-a-Number” (NaN) values, positive infinity, and negative infinity.some
Yes, Javascript does not have a distinct "integer" type, but it is still not uncommon to need to do this conversion. For instance, in my application users typed in a number (possibly including cents). I had to truncate the cents and display w/ commas. Step 1 was to convert to int.mcherm
also useful: speed comparison of all methods jsperf.com/math-floor-vs-math-round-vs-parseint/33c..
@karl: If I'm accepting input into a field, I might be able to control what characters I accept, but I could be doing all kinds of processing in Javascript, not just accepting user input. Even then I might want it for things like supporting paste.mcherm

10 Answers

1863
votes
var intvalue = Math.floor( floatvalue );
var intvalue = Math.ceil( floatvalue ); 
var intvalue = Math.round( floatvalue );

// `Math.trunc` was added in ECMAScript 6
var intvalue = Math.trunc( floatvalue );

Math object reference


Examples

Positive
// value=x        //  x=5          5<x<5.5      5.5<=x<6  

Math.floor(value) //  5            5            5
Math.ceil(value)  //  5            6            6
Math.round(value) //  5            5            6
Math.trunc(value) //  5            5            5
parseInt(value)   //  5            5            5
~~value           //  5            5            5
value | 0         //  5            5            5
value >> 0        //  5            5            5
value >>> 0       //  5            5            5
value - value % 1 //  5            5            5
Negative
// value=x        // x=-5         -5>x>=-5.5   -5.5>x>-6

Math.floor(value) // -5           -6           -6
Math.ceil(value)  // -5           -5           -5
Math.round(value) // -5           -5           -6
Math.trunc(value) // -5           -5           -5
parseInt(value)   // -5           -5           -5
value | 0         // -5           -5           -5
~~value           // -5           -5           -5
value >> 0        // -5           -5           -5
value >>> 0       // 4294967291   4294967291   4294967291
value - value % 1 // -5           -5           -5
Positive - Larger numbers
// x = Number.MAX_SAFE_INTEGER/10 // =900719925474099.1

// value=x            x=900719925474099    x=900719925474099.4  x=900719925474099.5
           
Math.floor(value) //  900719925474099      900719925474099      900719925474099
Math.ceil(value)  //  900719925474099      900719925474100      900719925474100
Math.round(value) //  900719925474099      900719925474099      900719925474100
Math.trunc(value) //  900719925474099      900719925474099      900719925474099
parseInt(value)   //  900719925474099      900719925474099      900719925474099
value | 0         //  858993459            858993459            858993459
~~value           //  858993459            858993459            858993459
value >> 0        //  858993459            858993459            858993459
value >>> 0       //  858993459            858993459            858993459
value - value % 1 //  900719925474099      900719925474099      900719925474099
Negative - Larger numbers
// x = Number.MAX_SAFE_INTEGER/10 * -1 // -900719925474099.1

// value = x      // x=-900719925474099   x=-900719925474099.5 x=-900719925474099.6

Math.floor(value) // -900719925474099     -900719925474100     -900719925474100
Math.ceil(value)  // -900719925474099     -900719925474099     -900719925474099
Math.round(value) // -900719925474099     -900719925474099     -900719925474100
Math.trunc(value) // -900719925474099     -900719925474099     -900719925474099
parseInt(value)   // -900719925474099     -900719925474099     -900719925474099
value | 0         // -858993459           -858993459           -858993459
~~value           // -858993459           -858993459           -858993459
value >> 0        // -858993459           -858993459           -858993459
value >>> 0       //  3435973837           3435973837           3435973837
value - value % 1 // -900719925474099     -900719925474099     -900719925474099
320
votes

Bitwise OR operator

A bitwise or operator can be used to truncate floating point figures and it works for positives as well as negatives:

function float2int (value) {
    return value | 0;
}

Results

float2int(3.1) == 3
float2int(-3.1) == -3
float2int(3.9) == 3
float2int(-3.9) == -3

Performance comparison?

I've created a JSPerf test that compares performance between:

  • Math.floor(val)
  • val | 0 bitwise OR
  • ~~val bitwise NOT
  • parseInt(val)

that only works with positive numbers. In this case you're safe to use bitwise operations well as Math.floor function.

But if you need your code to work with positives as well as negatives, then a bitwise operation is the fastest (OR being the preferred one). This other JSPerf test compares the same where it's pretty obvious that because of the additional sign checking Math is now the slowest of the four.

Note

As stated in comments, BITWISE operators operate on signed 32bit integers, therefore large numbers will be converted, example:

1234567890  | 0 => 1234567890
12345678901 | 0 => -539222987
98
votes

Note: You cannot use Math.floor() as a replacement for truncate, because Math.floor(-3.1) = -4 and not -3 !!

A correct replacement for truncate would be:

function truncate(value)
{
    if (value < 0) {
        return Math.ceil(value);
    }

    return Math.floor(value);
}
48
votes

A double bitwise not operator can be used to truncate floats. The other operations you mentioned are available through Math.floor, Math.ceil, and Math.round.

> ~~2.5
2
> ~~(-1.4)
-1

More details courtesy of James Padolsey.

41
votes

For truncate:

var intvalue = Math.floor(value);

For round:

var intvalue = Math.round(value);
26
votes

You can use the parseInt method for no rounding. Be careful with user input due to the 0x (hex) and 0 (octal) prefix options.

var intValue = parseInt(floatValue, 10);

EDIT: as a warning (from the comments section), please be aware that certain numeric values will be converted to their exponent form such as 1e21 which results in the incorrect decimal representation of "1"

19
votes

Bit shift by 0 which is equivalent to division by 1

// >> or >>>
2.0 >> 0; // 2
2.0 >>> 0; // 2
11
votes

In your case, when you want a string in the end (in order to insert commas), you can also just use the Number.toFixed() function, however, this will perform rounding.

7
votes

There are many suggestions here. The bitwise OR seems to be the simplest by far. Here is another short solution which works with negative numbers as well using the modulo operator. It is probably easier to understand than the bitwise OR:

intval = floatval - floatval%1;

This method also works with high value numbers where neither '|0' nor '~~' nor '>>0' work correctly:

> n=4294967295;
> n|0
-1
> ~~n
-1
> n>>0
-1
> n-n%1
4294967295
7
votes

One more possible way — use XOR operation:

console.log(12.3 ^ 0); // 12
console.log("12.3" ^ 0); // 12
console.log(1.2 + 1.3 ^ 0); // 2
console.log(1.2 + 1.3 * 2 ^ 0); // 3
console.log(-1.2 ^ 0); // -1
console.log(-1.2 + 1 ^ 0); // 0
console.log(-1.2 - 1.3 ^ 0); // -2

Priority of bitwise operations is less then priority of math operations, it's useful. Try on https://jsfiddle.net/au51uj3r/