Home > OS >  Using timeit to compare the execution time in milliseconds between different statements
Using timeit to compare the execution time in milliseconds between different statements

Time:01-02

I want to measure the execution times between several print statements which give the same result (after reading a book on python which states that using f-strings is more efficient than using str.format() and % placeholders). My python is v 3.8.8.

here is my example:

name = 'Kimberley'

f'Hello, {name}, how is your day?' # method 1

'Hello, {0}, how is your day?'.format(name) # method 2

'Hello, %(who)s, how is your day?' % {'who': name} # method 3 which should be the slowest one.

so first I have tried this which does not work because 'name' is not defined within the function.

import timeit
name = 'Kimberley'
timeit.timeit(stmt= "f'Hello, {name}, how is your day?'")

then I have tried this, however it gives the similar results of 0:00:00.000038 for each of the methods.

from timeit import default_timer as timer
from datetime import timedelta

# method 1
start = timer()

name = 'Kimberley'
f'Hello, {name}, how is your day?'

end = timer()
print(timedelta(seconds=end-start))


...
#method 3
start = timer()

name = 'Kimberley'
'Hello, %(who)s, how is your lamb?' % {'who': name} 

end = timer()
print(timedelta(seconds=end-start))

however, this is not right because the book says that method 1 , method 2 and method 3 take about 0.06, 0.16 and 0.21 milliseconds to execute, respectively.

So I wonder how can I use timeit() to measure the execution times correctly?

CodePudding user response:

default_timer is not the best way to measure tiny pieces of code, since it can be easily affected by other system processes, and the time taken is so short it needs run multiple times to be significant.

Instead, use timeit.timeit as follows, specifying test-specific variables inside a setup block.

from timeit import timeit

setup = """
name = "Kimberley"
"""

method1 = """f'Hello, {name}, how is your day?'"""
method2 = """'Hello, {0}, how is your day?'.format(name)"""
method3 = """'Hello, %(who)s, how is your lamb?' % {'who': name}"""
method4 = """Hello, %s, how is your lamb?' % (name,)"""

for method in (method1, method2, method3, method4):
    print(timeit(setup=setup, stmt=method))
# 0.0563660740153864
# 0.17292902698274702
# 0.18335944903083146
# 0.09785140998428687

Note of course that these times (ms) are the time for timeit to execute each statement 1000000 times.

I've also added in method4 which is faster than 3 since it doesn't have to do the 'mapping' from who to name.

CodePudding user response:

I have discovered another way with globals=globals() following the solution above.

setup = "name = 'Kimberley'"

method1 = "f'Hello, {name}, how is your day?'"
method2 = "'Hello, {0}, how is your day?'.format(name)"
method3 = "'Hello, %(who)s, how is your day?' % {'who': name}"
method4 = "'Hello, %s, how is your day?' % (name,)"

for method in (method1, method2, method3, method4):
    print(timeit(globals=globals(), stmt=method))
  • Related