Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Which is the efficient way to convert a float into an int in python?

I've been using n = int(n) to convert a float into an int.

Recently, I came across another way to do the same thing :

n = n // 1

Which is the most efficient way, and why?

like image 528
Srichakradhar Avatar asked Dec 09 '13 12:12

Srichakradhar


People also ask

Does Python convert float to int round?

Python has three ways to turn a floating-point value into a whole (integer) number: The built-in round() function rounds values up and down. The math. floor() function rounds down to the next full integer.

What is the correct way to convert a variable to an integer type Python?

To convert, or cast, a string to an integer in Python, you use the int() built-in function. The function takes in as a parameter the initial string you want to convert, and returns the integer equivalent of the value you passed.

Which function can be used to convert an integer to a float?

By using the float() function, we can convert integers to floats.


2 Answers

Test it with timeit:

$ bin/python -mtimeit -n10000000 -s 'n = 1.345' 'int(n)'
10000000 loops, best of 3: 0.234 usec per loop
$ bin/python -mtimeit -n10000000 -s 'n = 1.345' 'n // 1'
10000000 loops, best of 3: 0.218 usec per loop

So floor division is only a faster by a small margin. Note that these values are very close, and I had to crank up the loop repeat count to iron out random influences on my machine. Even with such a high count, you need to repeat the experiments a few times to see how much the numbers still vary and what comes out faster most of the time.

This is logical, as int() requires a global lookup and a function call (so state is pushed and popped):

>>> import dis
>>> def use_int(n):
...     return int(n)
... 
>>> def use_floordiv(n):
...     return n // 1
... 
>>> dis.dis(use_int)
  2           0 LOAD_GLOBAL              0 (int)
              3 LOAD_FAST                0 (n)
              6 CALL_FUNCTION            1
              9 RETURN_VALUE        
>>> dis.dis(use_floordiv)
  2           0 LOAD_FAST                0 (n)
              3 LOAD_CONST               1 (1)
              6 BINARY_FLOOR_DIVIDE 
              7 RETURN_VALUE        

It is the LOAD_GLOBAL and CALL_FUNCTION opcodes that are slower than the LOAD_CONST and BINARY_FLOOR_DIVIDE opcodes; LOAD_CONST is a simple array lookup, LOAD_GLOBAL needs to do a dictionary lookup instead.

Binding int() to a local name can make a small difference, giving it the edge again (as it has to do less work than // 1 floor division):

$ bin/python -mtimeit -n10000000 -s 'n = 1.345' 'int(n)'
10000000 loops, best of 3: 0.233 usec per loop
$ bin/python -mtimeit -n10000000 -s 'n = 1.345; int_=int' 'int_(n)'
10000000 loops, best of 3: 0.195 usec per loop
$ bin/python -mtimeit -n10000000 -s 'n = 1.345' 'n // 1'
10000000 loops, best of 3: 0.225 usec per loop

Again, you need to run this with 10 million loops to see the differences consistently.

That said, int(n) is a lot more explicit and unless you are doing this in a time-critical loop, int(n) wins it in readability over n // 1. The timing differences are too small to make the cognitive cost of having to work out what // 1 does here worthwhile.

like image 82
Martijn Pieters Avatar answered Sep 23 '22 15:09

Martijn Pieters


Although Martijn Pieters answered your question of what is faster and how to test it I feel like speed isn't that important for such a small operation. I would use int() for readability as Inbar Rose said. Typically when dealing with something this small readability is far more important; although, a common equation can be an exception to this.

like image 23
justengel Avatar answered Sep 23 '22 15:09

justengel