Sida 1 av 1

Sorting dictionary by values

InläggPostat: 27 sep 2016, 02:47
av alevor657
Hej!
Jag höll på med kmom05 i python och har fråga angående detta kod

Kod: Markera allt
    genexp = ((k, d1[k]) for k in sorted(d1, key=d1.get, reverse=True))


Jag har hittat det på stackoverflow men jag fattar inte riktigt hur det går till när koden sorterar dictionary by value som är integers

för att få tag på key/values så anväder man

Kod: Markera allt
for k, v in genexp:


Det skulle vara bra att ha en tydlig förklaring här på forumet!

Re: Sorting dictionary by values

InläggPostat: 27 sep 2016, 08:47
av mos
En vanlig dictionary är inte sorterad. Vill man ha den sorterad kan man göra om den till en lista.

Funktionen sorted löser det.

Kodexempel:
Kod: Markera allt
>>> d = {"a": 3, "b": 2, "c": 1}
>>> d
{'a': 3, 'b': 2, 'c': 1}
>>> sorted(d)
['a', 'b', 'c']
>>> sorted(d, reverse=True)
['c', 'b', 'a']
>>> sorted(d, key=d.get)
['c', 'b', 'a']
>>> sorted(d, key=d.get, reverse=True)
['a', 'b', 'c']
>>>


Konstruktionen key=d.get är ett sätt att sortera per value, istället för per key.

Så mycket för att sortera en dict per value.

Sen KAN MAN lägga dicten i en lista, eftersom en lista håller sin ordning till skillnad från en dict. Varje rad i dicten läggs som en tuple i listan.

Det man använder är något som kallas List Comprehensions som är ett kortare sätt att konstruera en loop för att tilldela en lista.
Se följande exempel.
Kod: Markera allt
>>> alist = []
>>> for x in range(3):
...     alist.append(x)
...
>>> alist
[0, 1, 2]


Samma sak med list comprehension.
Kod: Markera allt
>>> alist = [(x) for x in range(3)]
>>> alist
[0, 1, 2]


Så, summa summarum: Sortera dict per value och lägga i en lista som tuple via list comprehension.
Kod: Markera allt
>>> d
{'a': 3, 'b': 2, 'c': 1}
>>> alist = [(k, d[k]) for k in sorted(d, key=d.get, reverse=True)]
>>> alist
[('a', 3), ('b', 2), ('c', 1)]
>>> alist = [(k, d[k]) for k in sorted(d, key=d.get)]
>>> alist
[('c', 1), ('b', 2), ('a', 3)]



Ah, men din exempelkod använder inte list comprehensions utan generator expression.

Se skillnaden:
Kod: Markera allt
>>> alist = [(x) for x in range(3)]
>>> alist
[0, 1, 2]
>>> alist = ((x) for x in range(3))
>>> alist
<generator object <genexpr> at 0x101c11a40>


Eller hela exemplet:
Kod: Markera allt
>>> alist = [(k, d[k]) for k in sorted(d, key=d.get)]
>>> alist
[('c', 1), ('b', 2), ('a', 3)]
>>> alist = ((k, d[k]) for k in sorted(d, key=d.get))
>>> alist
<generator object <genexpr> at 0x101c119e8>
>>> for k, v in alist:
...     print("{} -> {}".format(k, v))
...
c -> 1
b -> 2
a -> 3


Ska man använda list comprehensions eller generator expressions?
http://stackoverflow.com/questions/4778 ... prehension

Skillnaden är att man får hela listan, eller ett generator objekt som man kan iterera runt.

Läs mer om list comprehension versus generator expressions.
https://docs.python.org/3/howto/functio ... rehensions

Re: Sorting dictionary by values

InläggPostat: 29 sep 2016, 11:12
av makreng
Mos (eller någon annan!) skulle du kunna bryta ner pseudokoden och förklara syntaxen närmare?

Kod: Markera allt
lista = [{k, dictionary[k]} for k in sorted(dictionary, key=dictionary.get, reverse = True)[:7]]


Vad precis skriver man när man skriver:
Kod: Markera allt
{k, dictionary[k]}
i början av listan?

Re: Sorting dictionary by values

InläggPostat: 29 sep 2016, 11:49
av makreng
När jag försöker använda koden så blandas nycklar och värden. Hur kan det vara så? Min output blir:

88: the
73: she
to: 71
56: and
51: was
51: a
41: it


koden:
Kod: Markera allt
    dictList = [{k, wordDict[k]} for k in sorted(wordDict, key=wordDict.get, reverse = True)[:7]]
    for k, v in dictList:
        print("{}: {}".format(k, v))

Re: Sorting dictionary by values

InläggPostat: 29 sep 2016, 11:55
av ceruza
Det är ingen pseudokod vad jag kan se, han har ju skrivit in det i tolken!

Kod: Markera allt
{k, dictionary[k]}



k är nyckeln i din dictionary, och du skapar här ett ny "mini dictionary" som bara har ett en nyckel/värde combo, och stoppar den i en lista.

Det kan vara mekigt att förstå python "list comprehension".
Den här resursen kanske hjälper dig förstå:
http://treyhunner.com/2015/12/python-list-comprehensions-now-in-color/

Re: Sorting dictionary by values

InläggPostat: 29 sep 2016, 12:31
av makreng
Tack, ska kolla länken, men behövs nog några användningar innan det sätter sig!

Re: Sorting dictionary by values

InläggPostat: 29 sep 2016, 12:40
av lrc
Se upp med tecknen -- det skall vara (k, dictionary[k]), inte {k, dictionary[k]}! Det förstnämnda skapar en tuple, det sisnämnda en mängd (set) -- inte en dictionary, vars syntax är {key: value}. Mängder har ingen definierad ordning, därav blandningen.