skip to navigation
skip to content

Python Wiki

Python Insider Blog

Python 2 or 3?

Help Fund Python

[Python resources in languages other than English]

Non-English Resources

Add an event to this calendar.

Times are shown in UTC/GMT.

Add an event to this calendar.

PEP: 274
Title: Dict Comprehensions
Version: 51119569c556
Last-Modified:  2012-05-01 13:47:47 +0200 (Tue, 01 May 2012)
Author: Barry Warsaw <barry at python.org>
Status: Final
Type: Standards Track
Created: 25-Oct-2001
Python-Version: 2.7, 3.0 (originally 2.3)
Post-History: 29-Oct-2001

Abstract

    PEP 202 introduces a syntactical extension to Python called the
    "list comprehension"[1].  This PEP proposes a similar syntactical
    extension called the "dictionary comprehension" or "dict
    comprehension" for short.  You can use dict comprehensions in ways
    very similar to list comprehensions, except that they produce
    Python dictionary objects instead of list objects.


Resolution

    This PEP was originally written for inclusion in Python 2.3.  It
    was withdrawn after observation that substantially all of its
    benefits were subsumed by generator expressions coupled with the
    dict() constructor.

    However, Python 2.7 and 3.0 introduces this exact feature, as well
    as the closely related set comprehensions.  On 2012-04-09, the PEP
    was changed to reflect this reality by updating its Status to
    Accepted, and updating the Python-Version field.  The Open
    Questions section was also removed since these have been long
    resolved by the current implementation.


Proposed Solution

    Dict comprehensions are just like list comprehensions, except that
    you group the expression using curly braces instead of square
    braces.  Also, the left part before the `for' keyword expresses
    both a key and a value, separated by a colon.  The notation is
    specifically designed to remind you of list comprehensions as
    applied to dictionaries.


Rationale

    There are times when you have some data arranged as a sequences of
    length-2 sequences, and you want to turn that into a dictionary.
    In Python 2.2, the dict() constructor accepts an argument that is
    a sequence of length-2 sequences, used as (key, value) pairs to
    initialize a new dictionary object.

    However, the act of turning some data into a sequence of length-2
    sequences can be inconvenient or inefficient from a memory or
    performance standpoint.  Also, for some common operations, such as
    turning a list of things into a set of things for quick duplicate
    removal or set inclusion tests, a better syntax can help code
    clarity.

    As with list comprehensions, an explicit for loop can always be
    used (and in fact was the only way to do it in earlier versions of
    Python).  But as with list comprehensions, dict comprehensions can
    provide a more syntactically succinct idiom that the traditional
    for loop.


Semantics

    The semantics of dict comprehensions can actually be demonstrated
    in stock Python 2.2, by passing a list comprehension to the
    built-in dictionary constructor:

    >>> dict([(i, chr(65+i)) for i in range(4)])

    is semantically equivalent to

    >>> {i : chr(65+i) for i in range(4)}

    The dictionary constructor approach has two distinct disadvantages
    from the proposed syntax though.  First, it isn't as legible as a
    dict comprehension.  Second, it forces the programmer to create an
    in-core list object first, which could be expensive.


Examples

    >>> print {i : chr(65+i) for i in range(4)}
    {0 : 'A', 1 : 'B', 2 : 'C', 3 : 'D'}

    >>> print {k : v for k, v in someDict.iteritems()} == someDict.copy()
    1

    >>> print {x.lower() : 1 for x in list_of_email_addrs}
    {'barry@zope.com'   : 1, 'barry@python.org' : 1, 'guido@python.org' : 1}

    >>> def invert(d):
    ...     return {v : k for k, v in d.iteritems()}
    ...
    >>> d = {0 : 'A', 1 : 'B', 2 : 'C', 3 : 'D'}
    >>> print invert(d)
    {'A' : 0, 'B' : 1, 'C' : 2, 'D' : 3}

    >>> {(k, v): k+v for k in range(4) for v in range(4)}
    ... {(3, 3): 6, (3, 2): 5, (3, 1): 4, (0, 1): 1, (2, 1): 3,
         (0, 2): 2, (3, 0): 3, (0, 3): 3, (1, 1): 2, (1, 0): 1,
         (0, 0): 0, (1, 2): 3, (2, 0): 2, (1, 3): 4, (2, 2): 4, (
         2, 3): 5}


Implementation

    All implementation details were resolved in the Python 2.7 and 3.0
    time-frame. 


References

    [1] PEP 202, List Comprehensions
        http://www.python.org/dev/peps/pep-0202/


Copyright

    This document has been placed in the public domain.