Sushim Mukul Dutta - 5 months ago 52

Python Question

I have a dictionary which has the following content :

`dict = {'P1' :361 , 'P2' : 361, 'P3' : 391, 'P6' : 361, 'P4':361, 'P5' :361}`

which needs to be sorted on basis of value in descending order. For any given item if the value is same to the item it is compared, it is to be sorted on the ascending order of key. Hence, the resultant value of the dict should be this.

`{'P3' : 391 , 'P1' : 361, 'P2': 361, 'P4': 361, 'P5': 361,'P6' : 361}`

I have achieved the first part using this :

`sorted_dict = OrderedDict(sorted(dict.items(), key=lambda t: t[1],reverse=True))`

However, I am uncertain how to go beyond that. I am assuming the comparator function typically can be something like this

`def comparator(item1,item2):`

if item1.value() == item2.value():

if item1.key()<item2.key():

return -1

if item1.key()>item2.key():

return 1

if item1.key() == item2.key():

return 0

if item1.value() < item2.value():

return -1

if item1.value() > item2.value():

return 1

I am unsure of how to implement this. Pardon my naivetÃ©, I am a beginner in Python and have little knowledge of the programming constructs in the language.

Answer

You can just use a slightly different lambda expression as the key for sorting.

```
sorted_dict = OrderedDict(sorted(dict.items(), key=lambda x: (-x[1], x[0])))
```

**Outputs**:

```
OrderedDict([('P3', 391), ('P1', 361), ('P2', 361), ('P4', 361), ('P5', 361), ('P6', 361)])
```

Supplying a `key`

is supplying a function to transform each item before comparison. So here, the anonymous lambda function supplies a sequence transformation used for sorting - sequences are sorted by comparing each element in turn. So we sort by the negative of the number (to invert the natural ascending -> descending), and should that compare equal we move on to the string for sorting, which sorts normally the way you intend it to (*at least for the sample provided*). You might need to make use of string natural sorting for larger numbers in your string.