[Python-ideas] dictionary constructor should not allow duplicate keys

Franklin? Lee leewangzhong+python at gmail.com
Tue May 3 20:25:02 EDT 2016

On May 3, 2016 3:21 PM, "Michael Selik" <michael.selik at gmail.com> wrote:
> On Mon, May 2, 2016 at 5:36 PM Luigi Semenzato <luigi at semenzato.com>
>> For context, someone ran into this problem in my team at Google (we
>> fixed it using pylint). I haven't seen any valid reason (in the bug
>> or elsewhere) in favor of these constructor semantics. From the
>> discussions I have seen, it seems just an oversight in the
>> implementation/specification of dictionary literals.  I'd be happy to
>> hear stronger reasoning in favor of the status quo.
> Do you feel that "prefer status quo" is not strong reasoning?
> Your word choice of "[no] valid reason" is interesting. In the bug
tracker discussion, folks argue that the problem is easily solved with code
style standards and static analyzers. I thought that was valid.

"X is detectable", whether by tools, or by magic imps yelling at you when
you do it, is not an argument for X.

When asking for a useful purpose for the current semantics, "prefer the
status quo" is not strong enough. "Errors should never pass silently," and
there is an argument on the table that duplicate spelled-out keys are
probably written in error. He isn't shifting the burden, he's putting the
ball in your court.

> Literal dicts syntactically may have any expression as the key. Creating
a special case for the parser to enforce uniqueness of number and string
literals as keys seems more trouble than its worth.

That is an argument. Literal keys, or a single name repeated in the key
list, might be an error, but you can't say the same about expressions. If
you only error on literal keys, then there is an inconsistency between
literals and expressions.

By the way, unless [[the name is guaranteed not to be rebound in a closure
called within the dict display]], multiple items with the same variable
name as key isn't necessarily an error:

    def f():
        def g():
          nonlocal x
          x += 1
          return x
        return {x: g(), x: g(), x: g()}

    # {2: 2, 3: 3, 4: 4}

"Don't do that" doesn't say what the compiler behavior should be: should it
analyze for nonlocal closures, or should it only check literals?
-------------- next part --------------
An HTML attachment was scrubbed...
URL: <http://mail.python.org/pipermail/python-ideas/attachments/20160503/e1066b2d/attachment-0001.html>

More information about the Python-ideas mailing list