Сортировка подсчитанного списка в Python - PullRequest
2 голосов
/ 30 августа 2011

(Я новичок в любом виде программирования, поэтому, пожалуйста, будьте точны, когда сможете ответить). Проблема: Я написал программу для решения pythonchallenge.com уровня 2. Программа работает, но результаты грязные.Я хочу отсортировать результаты подсчета символов в красивый список.Когда я пытаюсь отсортировать результаты подсчета символов с помощью sorted (), он удаляет все подсчеты и просто дает мне список символов, которые были в моей строке.Мне нужно иметь возможность видеть, сколько каждого персонажа было в моем файле.В любом случае вот код:

countstring = open('pagesource.txt').read()

charcount = {}

for x in countstring:
    charcount[x] = charcount.get(x, 0) + 1

print charcount

это то, что я получаю в cmd:

>>> {'\n': 1219, '!': 6079, '#': 6115, '%': 6104, '$': 6046, '&': 6043, ')': 6186, '
(': 6154, '+': 6066, '*': 6034, '@': 6157, '[': 6108, ']': 6152, '_': 6112, '^':
 6030, 'a': 1, 'e': 1, 'i': 1, 'l': 1, 'q': 1, 'u': 1, 't': 1, 'y': 1, '{': 6046
, '}': 6105}

, если я добавлю к нему функцию sorted (), такую ​​как print sorted (charcount)получите это в cmd:

>>> ['\n', '!', '#', '$', '%', '&', '(', ')', '*', '+', '@', '[', ']', '^', '_', 'a'
, 'e', 'i', 'l', 'q', 't', 'u', 'y', '{', '}']

Спасибо за ваши решения, и если вы можете потратить время на добавление комментариев к вашему коду, объясняющих, что все делает, я был бы очень признателен!

Ответы [ 6 ]

3 голосов
/ 30 августа 2011

Вы действительно должны использовать класс Counter вместо того, чтобы изобретать свое собственное колесо.

charcount - это словарь, и словари не имеют неявного порядка сортировки. Поэтому нам придется преобразовать его в список, который можно отсортировать. Каждая запись в этом списке будет кортеж из числа и символа.

charcount.items() уже дает нам список, который выглядит как [('\n', 1219), ('!', 6079)]. К сожалению, если бы мы отсортировали этот список, он сначала отсортировал бы по символам, а затем (если символы когда-либо были равны) по количеству, а не наоборот. Следовательно, нам нужна ключевая функция , чтобы сообщить сортировке сначала посмотреть на счетчик, а затем (если количество равно) символ. К счастью, наша ключевая функция действительно проста; он просто обменивается на кортеж:

lambda (char,count): (count, char)

В качестве альтернативы, мы можем использовать понимание списка, чтобы поменять значения, получить что-то вроде: [('\n', 1219), ('!', 6079)], затем отсортировать и затем поменять значения снова.

charcount_list = sorted(charcount.items(), key=lambda (char,count):(count, char))

charcount_list теперь будет:

[('a', 1), ('e', 1), ('i', 1), ('l', 1), ('q', 1), ('t', 1), ('u', 1), ('y', 1),
 ('\n', 1219), ('^', 6030), ('*', 6034), ('&', 6043), ('$', 6046), ('{', 6046),
 ('+', 6066), ('!', 6079), ('%', 6104), ('}', 6105), ('[', 6108), ('_', 6112),
 ('#', 6115), (']', 6152), (' (', 6154), ('@', 6157), (')', 6186)]

Если вам нужен обратный порядок, просто укажите аргумент reverse=True для sorted .

2 голосов
/ 30 августа 2011
>>> from operator import itemgetter
>>> sorted(charcount.items(), key=itemgetter(1))
[('a', 1), ('e', 1), ('i', 1), ('l', 1), ('q', 1), ('u', 1), ('t', 1), ('y', 1), ('\n', 1219), ('^', 6030), ('*', 6034), ('&', 6043), ('$', 6046), ('{', 6046), ('+', 6066), ('!', 6079), ('%', 6104), ('}', 6105), ('[', 6108), ('_', 6112), ('#', 6115), (']', 6152), (' (', 6154), ('@', 6157), (')', 6186)]
0 голосов
/ 30 августа 2011

Словари (что означает {}) - это неупорядоченные коллекции.Это означает, что вы не можете сортировать их осмысленно.Я предлагаю сохранить информацию в виде списка кортежей [(), ...] и затем отсортировать их на основе этого.

foo = [('a', 123), ('b', 345)]

def key_function(x):
    return x[1]

sorted_list = sorted(foo, key_function)
print sorted_list

Как видите, сортировка принимает необязательный второй параметр.Цель этого параметра - предоставить функцию, которая сообщает отсортированному как что-то сортировать.Все, что вы делаете, это разбиваете информацию в каждом кортеже в списке, чтобы получить значение, которое можно упорядочить, поскольку вы не можете реально упорядочить список кортежей каким-либо значимым образом.

Имеет смысл?

Его также можно записать так: print sorted(foo, key=lambda (x,y): y)

Лямбда просто означает встроенную функцию без имени, и она позволяет вам разбивать кортеж по-другому.

Вы можете увидеть, как это работает, выполнив print [y for (x,y) in sorted_list]

Вы даже можете переопределить функцию ключа, как показано ниже:

def key_function(x):
    x,y = x
    return y

Кстати, я ставлю только скобки передясность.Если вы не определяете функцию, то запятая - это конструктор кортежей.

0 голосов
/ 30 августа 2011

Словарь повторяется по ключу, поэтому вы получаете отсортированный список ключей при передаче словаря в sorted. Сортируйте кортежи элементов словаря по значению, чтобы получить список отсортированных кортежей.

sorted_charcount = sorted(charcount.items(), key=lambda item: item[1])

Если вы используете Python 2.7+, вы можете использовать список кортежей для инициализации OrderedDict, который будет поддерживать отсортированный порядок кортежей элементов.

0 голосов
/ 30 августа 2011

charcount - это dict (словарь).Итерирование словаря итерирование по его ключам, поэтому sorted() приводит к сортированному списку ключей.

Вам необходимо получить список элементов, а затем отсортировать его по второму значению:

sorted(charcount.items(), key=lambda t: t[1])
0 голосов
/ 30 августа 2011
sorted(charcount.items(), key=lambda item: item[1])
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...