Python list comprehension for dictionaries in dictionaries?

后端 未结 5 2130
借酒劲吻你
借酒劲吻你 2021-01-03 19:46

I just learned about list comprehension, which is a great fast way to get data in a single line of code. But something\'s bugging me.

In my test I have this kind of

相关标签:
5条回答
  • 2021-01-03 20:22

    You can get a list of the values of a dictionary d with d.values(). Your list comprehension should work using that, although I'm a little unclear what exactly you want the output to be.

    0 讨论(0)
  • 2021-01-03 20:25

    Sounds like you want something like:

    my_dict = {'test1420': {'y': '060', 'x': '070', 'fname': 'test1420'},
               'test277' : {'y': '072', 'x': '094', 'fname': 'test277'}}
    
    
    new_dict = dict((k,v) for k,v in my_dict.items() 
                        if 92 < int(v['x']) < 95 and 70 < int(v['y']) < 75)
    

    Some notes on this code:

    1. I'm using a generator expression instead of a list comprehension
    2. Python lets you combine inequality tests as low < value < high
    3. The dict() constructor takes an iterable of key/value tuples to create a dictionary
    0 讨论(0)
  • 2021-01-03 20:32

    Is there another way?

    Why not consider the use of some lightweight objects?

    You can still use list comprehensions for gathering or filtering the objects, and gain a lot in clarity / extensibility.

    >>> class Item(object):
    ...     def __init__(self, x, y, name):
    ...         self.x = x
    ...         self.y = y
    ...         self.name = name
    ... 
    >>> list_items = []
    >>> list_items.append(Item(x=70, y=60, name='test1420'))                        
    >>> list_items.append(Item(x=94, y=72, name='test277'))                         
    >>> items_matching = [item for item in list_items 
                          if 92 < item.x < 95 and 70 < item.y < 75]
    >>> for item in items_matching:
    ...     print item.name
    ... 
    test277
    >>> first_item = items_matching[0]
    >>> first_item.x += 50
    >>> first_item.x
    144
    
    0 讨论(0)
  • 2021-01-03 20:38

    You can do this:

    s = dict([ (k,r) for k,r in mydict.iteritems() if r['x'] > 92 and r['x'] < 95 and r['y'] > 70 and r['y'] < 75 ])
    

    This takes a dict as you specified and returns a 'filtered' dict.

    0 讨论(0)
  • 2021-01-03 20:39

    If dct is

    {'test1420': {'y': '060', 'x': '070', 'fname': 'test1420'},
     'test277': {'y': 72, 'x': 94, 'fname': 'test277'},}
    

    Perhaps you are looking for something like:

    [ subdct for key,subdct in dct.iteritems() 
      if 92<subdct['x']<95 and 70<subdct['y']<75 ]
    

    A little nicety is that Python allows you to chain inequalities:

    92<dct[key]['x']<95
    

    instead of

    if r['x'] > 92 and r['x'] < 95
    

    Note also that above I've written a list comprehension, so you get back a list (in this case, of dicts).

    In Python3 there are such things as dict comprehensions as well:

    { n: n*n for n in range(5) } # dict comprehension
    {0: 0, 1: 1, 2: 4, 3: 9, 4: 16}
    

    In Python2 the equivalent would be

    dict( (n,n*n) for n in range(5) )
    

    I'm not sure if you are looking for a list of dicts or a dict of dicts, but if you understand the examples above, it is easy to modify my answer to get what you want.

    0 讨论(0)
提交回复
热议问题