Natalie
Natalie

Reputation: 447

Sorting python dictionary within dictionary

I am trying to sort a dictionary of dictionaries. My dictionary looks like this, except there are about several million more entries with varying usernames, dates, and numbers:

{'RandomUserName': defaultdict(<type 'int'>, {'6/30/15': 2}), 
'AnotherRandomUserName': defaultdict(<type 'int'>, {'5/25/16': 8}), 
'AThirdRandomUserName': defaultdict(<type 'int'>, {'1/12/15': 5})}

I want to sort this dictionary based on the numbers at the end of the entries. I know it is impossible to sort a dictionary and that you can only return a sorted representation. That is exactly what I am trying to do.

I have been looking around for answers on how to sort dictionary within dictionary but all the answers assume we know the key before the value. What if we don't? How can I sort this based on the integer at the end?

Thanks so much, I appreciate any answers!

Upvotes: 1

Views: 101

Answers (1)

Thundzz
Thundzz

Reputation: 695

First solution that comes to my mind is to flatten the dictionnary, and then sort the resulting list.

For example:

dictionary_of_dictionaries = {
    'RandomUserName':  {'6/30/15': 2}, 
    'AnotherRandomUserName': {'5/25/16': 8}, 
    'AThirdRandomUserName': {'1/12/15': 5}
}


flattened = [(k,) + tuple(dic.iteritems()) for k, dic in dictionary_of_dictionaries.iteritems()]
print flattened

Prints:

[('AnotherRandomUserName', ('5/25/16', 8)), ('RandomUserName', ('6/30/15', 2)), ('AThirdRandomUserName', ('1/12/15', 5))]

And then sorting this list

flattened.sort(key= lambda x:x[1][1])
print flattened

Which then prints the entries in the order you want them.

[('RandomUserName', ('6/30/15', 2)), ('AThirdRandomUserName', ('1/12/15', 5)), ('AnotherRandomUserName', ('5/25/16', 8))]

Please not that in this first solution, I am supposing that the second dictionary only contains one date field. With a more complex example you have to make sure that the tuples of the inner dictionnary are always flattened in the same order.


A solution that solves this problem (won't be very performant if your inner dictionaries contain tons of fields)

dictionary_of_dictionaries = {
    'RandomUserName':  {'6/30/15': 2 , 'name' : 'foo'}, 
    'AnotherRandomUserName': {'5/25/16': 8, 'name' : 'bar'}, 
    'AThirdRandomUserName': {'1/12/15': 5, 'name' : 'baz' }
}


flattened = [(k,) + tuple(sorted(dic.iteritems(), key=lambda x: x[0])) for k, dic in dictionary_of_dictionaries.iteritems()]
print flattened


flattened.sort(key= lambda x:x[1][1])
print flattened

Upvotes: 1

Related Questions