[Python-Dev] performance of {} versus dict()

Steven D'Aprano steve at pearwood.info
Wed Nov 14 12:21:03 CET 2012


On 14/11/12 21:00, Chris Withers wrote:
> On 14/11/2012 09:58, Merlijn van Deen wrote:
>> On 14 November 2012 10:12, Chris Withers <chris at simplistix.co.uk> wrote:
>>> ...which made me a little sad
>>
>> Why did it make you sad? dict() takes 0.2µs, {} takes 0.04µs. In other
>> words: you can run dict() _five million_ times per second, and {}
>> twenty-five million times per second. That is 'a lot' and 'a lot'. It
>> also means you are unlikely to notice the difference in real-world
>> code. Just use the one you feel is clearer in the situation, and don't
>> worry about micro-optimalization.
>
> I'm inclined to agree, but it makes me sad for two reasons:
>
> - it's something that people get hung up on, for better or worse. (if it
>  wasn't, Doug wouldn't have written his article)

People get hung up on all sorts of things. I would hate to think we would
complicate the implementation to pander to pointless micro-optimization.
I'm sure that there are many far more important things than this.


> - it can make a difference, for example setting up a dict with many keys
>at the core of a type loop.

Ah yes, the semi-mythical "tight loop".

I've never come across one of these tight loops that creates a dict with
many keys in a tight loop, and then apparently fails to actually use it
for anything useful. For if it did, surely the actual work done with the
dict is going to outweigh the setup cost for all but the most trivial
applications. I find it hard to get uptight about a small inefficiency
in trivial applications that don't do much.

Show me a non-toy use-case where creating dicts is an actual bottleneck,
and I'll revise my position.


> Without looking at implementation, they should logically perform the same...

I disagree. Calling dict() has to do a name lookup, and then a function
call. That alone is almost 2.5 times as expensive as creating a dict
literal on my machine:

[steve at ando ~]$ python3.3 -m timeit "d = {}"
10000000 loops, best of 3: 0.17 usec per loop
[steve at ando ~]$ python3.3 -m timeit "d = dict()"
1000000 loops, best of 3: 0.416 usec per loop

Then you have the function call itself, which engages the argument parsing
mechanism, which does more work than dict literal syntax. For example, it
checks for duplicate keyword arguments, while dict literals happily accept
duplicate keys.

It's hardly a surprise that dict() is slower than {}.



-- 
Steven


More information about the Python-Dev mailing list