Should constants be introduced to Python?
Chris Angelico
rosuav at gmail.com
Thu Nov 16 17:39:20 EST 2017
On Fri, Nov 17, 2017 at 9:27 AM, Terry Reedy <tjreedy at udel.edu> wrote:
> CPython, at least, already has anonymous constant objects. Number and
> string literals are turned into objects when parsed. I presume that all
> implementations do this. Some constant expressions are replaced by
> (constant) objects during compiling, instead of when running. For instance
> "n = 10 + 3' will run as 'n = 13', and "for lang in ('C', 'Java', 'Python')
> will have the tuple pre-computed (whereas "for lang in ['C', 'Java',
> 'Python] will have to construct the list each time run).
Just to thoroughly confuse people, CPython can actually optimize one
into the other...
>>> def f():
... for lang in ['C', 'Java', 'Python']:
... print(lang)
...
>>> dis.dis(f)
2 0 SETUP_LOOP 20 (to 22)
2 LOAD_CONST 4 (('C', 'Java', 'Python'))
4 GET_ITER
>> 6 FOR_ITER 12 (to 20)
8 STORE_FAST 0 (lang)
3 10 LOAD_GLOBAL 0 (print)
12 LOAD_FAST 0 (lang)
14 CALL_FUNCTION 1
16 POP_TOP
18 JUMP_ABSOLUTE 6
>> 20 POP_BLOCK
>> 22 LOAD_CONST 0 (None)
24 RETURN_VALUE
Since there's no way to get a reference to the underlying list during
iteration (which would allow you to mutate it), Python can happily
pretend that you used a tuple. Similarly with membership tests:
>>> dis.dis("x in [1,2,3,4,5]")
1 0 LOAD_NAME 0 (x)
2 LOAD_CONST 5 ((1, 2, 3, 4, 5))
4 COMPARE_OP 6 (in)
6 RETURN_VALUE
>>> dis.dis("x in {1,2,3,4,5}")
1 0 LOAD_NAME 0 (x)
2 LOAD_CONST 5 (frozenset({1, 2, 3, 4, 5}))
4 COMPARE_OP 6 (in)
6 RETURN_VALUE
However, outside of these special optimization cases, you're right
that a tuple is a constant and a list gets built at run time.
ChrisA
More information about the Python-list
mailing list