简体   繁体   中英

How to shorten this nested list comprehension?

This question is a continuation of this one: Comprehension list and output <generator object.<locals>.<genexpr> at 0x000002C392688C78>

I was oriented to create a new question. I have a few dicts inside another dict. And they get pretty big sometimes, since I'm keeping them in log I would like to limit the size of them to 30 'items' (key:value).

So I tried something like this: (In the example I limit the size to two)

main_dict = {
    'A':{
        'a1': [1,2,3],
        'a2': [4,5,6]
        },
    'B': {
        'b1': [0,2,4],
        'b2': [1,3,5]
        }
    }

print([main_dict[x][i][:2] for x in main_dict.keys() for i in main_dict[x].keys()])

The output I get is this:

[[1, 2], [4, 5], [0, 2], [1, 3]]

What I expected was this:

['A':['a1':[1, 2],'a2':[4, 5]], 'B':['b1':[0, 2], 'b2':[1, 3]]]

Or something like that. It doesn't have to be exactly that, but I need to know what value belongs to what dict, which isn't clear in the output I end up getting.

To put it simple all I want is to cut short the sub-dicts inside the dictionary. Elegantly, if possible.

Try this:

print({key: {sub_key: lst[:2] for sub_key, lst in sub_dict.items()}
       for key, sub_dict in main_dict.items()})

Note the use of {} (dict comprehension) instead of [] (list comprehension)

This is a nice clean way to do it in one line, without altering the original dictionary:

print({key: {sub_k: ls[:2] for sub_k, ls in sub_dict.items()} for key, sub_dict in main_dict.items()})

Output:

{'A': {'a1': [1, 2], 'a2': [4, 5]}, 'B': {'b1': [0, 2], 'b2': [1, 3]}}

Your original trial used list comprehension [] , but this case actually needs dict comprehension {} .

A more efficient approach is to use nested for loops to delete the tail end of the sub-lists in-place:

for d in main_dict.values():
    for k in d:
        del d[k][2:]

main_dict becomes:

{'A': {'a1': [1, 2], 'a2': [4, 5]}, 'B': {'b1': [0, 2], 'b2': [1, 3]}}
d = {'A':{
         'a1': [1,2,3],
         'a2': [4,5,6],
         'a3': [7,8,9]
         },
     'B':{
         'b1': [0,2,4],
         'b2': [1,3,5]
         }
     }

If the dictionaries are only nested one-deep

q = []
for k,v in d.items():
   keys, values = v.keys(), v.values()
   values = (value[:2] for value in values)
   q.append((k,tuple(zip(keys,values))))

I have rewrote my code based on the comments provided. See below.

my_dict = {}

for key, value in main_dict.iteritems():
    sub_dict = {}
    for sub_key, sub_value in value.iteritems():
        sub_dict[sub_key] = sub_value[:2] 
    my_dict[key] = sub_dict

print my_dict

This will give you something that looks like this, and save it to a separate variable.

{'A': {'a1': [1, 2], 'a2': [4, 5]}, 'B': {'b1': [0, 2], 'b2': [1, 3]}}

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM