0

I have this list of dictionaries, which are already sorted based on the first values. How do I continue to sort this list based on its second values as well?

Here is my list of dictionaries:

[{'P3': [7, 117]}, {'P8': [14, 88]}, {'P2': [19, 102]}, {'P4': [19, 95]}]

Desired outcome:

[{'P3': [7, 117]}, {'P8': [14, 88]}, {'P4': [19, 95]}, {'P2': [19, 102]}]

I am in the process of completing a Shortest Job First scheduling assignment in Python. The first value of each key(process) is the cpu burst and the second value is the arrival time, so I would need P4 to go before P2 since its arrival time comes first and they have the same cpu burst.

Dee
  • 13
  • 3

1 Answers1

0

For starters, If you want to just sort list of the dictionary with the list values you can use the one line of python code as below:

d = [{'P3': [7, 117]}, {'P8': [14, 88]}, {'P2': [19, 102]}, {'P4': [19, 95]}]  # assign the dictionary value
sort_by_first = sorted(d, key=lambda x: list(x.values()))

Output:

[{'P3': [7, 117]}, {'P8': [14, 88]}, {'P4': [19, 95]}, {'P2': [19, 102]}]

sorted() function in python accepts optional keyword argument key where you can pass a custom function to look for the key and I just made a lambda function which will sort list of dictionary d by its value list list(x.values())

In python list comparison results as follow:

In [1]: [19, 95] < [19, 102]
Out[1]: True

In [2]: [19, 95] < [19, 95]
Out[2]: False

In [3]: [19, 95] < [19, 5]
Out[3]: False

Update:

lambda function can be replaced with lambda x: next(iter(x.values())) where instead of typecasting value from dict_values is extracted as per this answer.

Gahan
  • 4,075
  • 4
  • 24
  • 44
  • Please add **some** explanation to your "one line of python code" for the sake of starters – Sheldore Oct 31 '18 at 17:21
  • No need to cast to a list.`lambda x: x.values()` should be enough which will return an iterable anyways – mad_ Oct 31 '18 at 17:30
  • @mad_ it won't work as key of dictionaries are unknown and hence calling .values() returns `dict_values` which does not support `<` operator – Gahan Oct 31 '18 at 17:32
  • @Gahan then it should not work by casting as well. Try `d={'a':[1]}; type(d.values())`;d.values() will be a list already. no need to cast. lambda is iterating each element of the `list` which is actually a dict. in your case intermediate `x` is actually a `dict` and `dict.values()` will return all the values contained inside the dict irrespective of keys. – mad_ Oct 31 '18 at 17:40
  • @mad_ I think you are talking about python 2.x but user explicitly tagged python 3.x and in python 3.x you need to cast dict.values() to list to access values by index – Gahan Oct 31 '18 at 17:43
  • oh yeah.. using both versions together is a nightmare sometimes because they behave so differently even in small cases. Sorry my bad.Thanks though – mad_ Oct 31 '18 at 17:47