Уведомления

Группа в Telegram: @pythonsu

#1 Янв. 3, 2018 15:23:52

marvellik
Зарегистрирован: 2016-05-15
Сообщения: 639
Репутация: +  73  -
Профиль   Отправить e-mail  

Сортировка словаря

может как то так? я задал словарь вручную поэтому год в списке типа int а у вас при чтении из файла будет str что при сортировке даст другой результат. думаю эту задачу решите

 babynames = { 'София, Софья': {
                        2012: [3841, 6.0], 
                        2010: [3668, 6.2],
                        2005: [2127, 4.8],
                        2000: [826, 2.4],
                        1990: [193, 0.4]},
                        
                        'Виктория': {
                        2012: [2219, None],
                        2010: [1994, None],
                        2005: [1829, None],
                        2000: [1076, None],
                        1990: [1033, None]},
              
                       'Мария, Марья' : {
                        2012: [3735 ,5,8],
                        2010: [1994, None],
                        2005: [1829, None],
                        2000: [1076, None],
                        1990: [1033, None],}
              }
def print_names(babynames ):
    
    def selekt(key):
            if year  in babynames[key].keys():
                return [key] + [ x for x in babynames[key][year] if x ]
            
    year = int(input('-->>>  '))
    
    result = [selekt(key) for key in babynames]
    for i in sorted(result,key = lambda x : x[1],reverse = True):
        print(*i)
print_names(babynames)
)
ну и несколько пробных результатов
–>>> 1990
Виктория 1033
Мария, Марья 1033
София, Софья 193 0.4
>>>
=============== RESTART: ===============
–>>> 2005
София, Софья 2127 4.8
Виктория 1829
Мария, Марья 1829
>>>
=============== RESTART: ===============
–>>> 2012
София, Софья 3841 6.0
Мария, Марья 3735 5 8
Виктория 2219

Отредактировано marvellik (Янв. 3, 2018 15:36:44)

Офлайн

#2 Янв. 4, 2018 17:30:09

SomethingButNotNickName
Зарегистрирован: 2017-12-19
Сообщения: 75
Репутация: +  0  -
Профиль   Отправить e-mail  

Сортировка словаря

marvellik
может как то так? я задал словарь вручную поэтому год в списке типа int а у вас при чтении из файла будет str что при сортировке даст другой результат. думаю эту задачу решите
Ну результат выдается корректный.
Спасибо, осталось понять как оно работает. С ходу разобраться не удалось, буду думать.

Офлайн

#3 Янв. 4, 2018 19:16:54

marvellik
Зарегистрирован: 2016-05-15
Сообщения: 639
Репутация: +  73  -
Профиль   Отправить e-mail  

Сортировка словаря

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

Офлайн

#4 Янв. 5, 2018 03:35:42

py.user.next
От:
Зарегистрирован: 2010-04-29
Сообщения: 10003
Репутация: +  857  -
Профиль   Отправить e-mail  

Сортировка словаря

  
>>> babynames = {
...     'София, Софья': {
...         2012: [3841, 6.0],
...         2010: [3668, 6.2],
...         2005: [2127, 4.8],
...         2000: [826, 2.4],
...         1990: [193, 0.4],
...     },
...     'Виктория': {
...         2012: [2219, None],
...         2010: [1994, None],
...         2005: [1829, None],
...         2000: [1076, None],
...         1990: [1033, None],
...     },
...     'Полина': {
...         2012: [2218, 1.0],
...         2010: [1993, 2.5],
...         2005: [1828, 3.0],
...         2000: [1075, 4.5],
...         1990: [1032, 5.0],
...     },
... }
>>> 
>>> def search_by_year(data, year):
...     return ([k] + v_data[year] for k, v_data in data.items()
...             if year in v_data)
... 
>>> def sort_by_number(seq):
...     return sorted(seq, key=lambda i: i[1], reverse=True)
... 
>>> def print_names(seq):
...     for name, count, weight in seq:
...         print('{:10}\t{}\t{}'.format(name, count, weight or ''))
... 
>>> print_names(sort_by_number(search_by_year(babynames, 2012)))
София, Софья    3841    6.0
Виктория        2219
Полина          2218    1.0
>>>



Отредактировано py.user.next (Янв. 5, 2018 03:40:06)

Офлайн

#5 Янв. 8, 2018 17:52:23

SomethingButNotNickName
Зарегистрирован: 2017-12-19
Сообщения: 75
Репутация: +  0  -
Профиль   Отправить e-mail  

Сортировка словаря

Возник вопрос.
Ваш код:

py.user.next
 >>> def search_by_year(data, year):
...     return ([k] + v_data[year] for k, v_data in data.items()
...             if year in v_data)
... 
>>> def sort_by_number(seq):
...     return sorted(seq, key=lambda i: i[1], reverse=True)
... 
>>> def print_names(seq):
...     for name, count, weight in seq:
...         print('{:10}\t{}\t{}'.format(name, count, weight or ''))
... 
>>> print_names(sort_by_number(search_by_year(babynames, 2012)))
София, Софья    3841    6.0
Виктория        2219
Полина          2218    1.0
>>>
>>>
Зачем третья строка?
  
...             if year in v_data) 
Проверка на наличие заданного года в словаре? Чтобы в случае некорректного года скрипт не выдал ошибку KeyError? И все? Или тут, что-то еще чего я не понял…

Офлайн

#6 Янв. 8, 2018 18:10:08

SomethingButNotNickName
Зарегистрирован: 2017-12-19
Сообщения: 75
Репутация: +  0  -
Профиль   Отправить e-mail  

Сортировка словаря

И еще вопрос.
Мне предложили два варианта решения marvellik и py.user.next.
Оба реализуют одну и ту же логику:
1) выбрать нужные данные из словаря в некий служебный список;
2) сортировать список;
3) напечатать результат.
В обоих случаях выполняются одни и те же действия => время работы будет одинаково, так?
Но в случае решения marvellik'a этот список реально существует, под него выделена переменная, к нему можно обратиться после окончания работы функции. А у py.user.next списку не дано имени, он существует только внутри функций, и насколько я понимаю, после окончания работы функции стирается из памяти.

Соответственно решение от py.user.next более рационально с точки зрения экономии памяти, так?

Офлайн

#7 Янв. 9, 2018 02:01:22

py.user.next
От:
Зарегистрирован: 2010-04-29
Сообщения: 10003
Репутация: +  857  -
Профиль   Отправить e-mail  

Сортировка словаря

SomethingButNotNickName
Зачем третья строка?
Если у кого-то запрашиваемый год есть, а кого-то запрашиваемого года нет, то того, у кого года нет, не надо включать в результат и обрабатывать не надо. А того, у кого год есть, надо включить в результат, только перед этим ещё обработать там, чтобы результат был простым и чтобы не нужно было потом копаться в нём, чтобы что-то достать.

SomethingButNotNickName
Но в случае решения marvellik'a этот список реально существует, под него выделена переменная, к нему можно обратиться после окончания работы функции. А у py.user.next списку не дано имени, он существует только внутри функций, и насколько я понимаю, после окончания работы функции стирается из памяти.
При сортировке список всё равно будет воссоздан, потому что сортировка через sorted() не может отсортировать на лету, ей нужно обязательно все элементы перебрать в каждом случае. Поэтому там возвращается список всегда, даже если ты подавал итератор какой-нибудь.
Мой вариант рациональнее потому, что там всё разделено по отдельным функциям. То есть за то, как выводится что-то, отвечает отдельная функция. За то, как сортируется что-то, отвечает отдельная функция. За то, как фильтруется что-то, отвечает отдельная функция. Допустим, тебе надо поменять вывод, например, - ты берёшь функцию, отвечающую за вывод, выдёргиваешь её и переписываешь только её; остальную программу тебе не надо трогать - всё работает как часы. Или тебе надо поменять сортировку - ты точно так же берёшь функцию, где происходит сортировка, и переделываешь только её. Ну и так далее.

А marvellik, если ему надо будет что-то из этого поменять, он сначала будет искать, где это находится в коде. А код бывает свой, а бывает не свой, а бывает даже твой, но который ты писал пять лет назад и в котором ты даже не можешь вспомнить, что это за код вообще и про что он и что там было тогда. Вот нашёл, к примеру, место через час, очертил его и решил менять. И тут оказывается, что от этого места зависит ещё какое-то место и из-за этого его тоже надо менять. И вот в конце выясняется, что менять надо вообще всё, потому что одно зависит от другого, а другое - от третьего. И заканчивается всё тем, что там 5000 строк и надо либо всё писать заново, либо ничего нельзя трогать, потому что всё остальное сломается. И в результате он начинает (обычно так происходит) вставлять хаки в код, которые в итоге всё ещё больше усугубляют. Ну это как идёт инженер по плохо построенному зданию, видит, что балка оторвалась, берёт верёвку и приматывает эту балку, потому что перестраивать это всё времени нет. А потом весь дом покрывается такими примотками, потому что постоянно что-то отрывается, и потом этот дом спокойненько складывается. Вот его код - это такой дом, в котором балки уже на соплях держатся, их ещё даже не приматывали, потому что дом только построили, его ещё никто не юзал. А при использовании оно полезет всё - надо то поменять, надо это поменять, надо туда это подсоединить, надо сюда это подсоединить.



Отредактировано py.user.next (Янв. 9, 2018 02:05:33)

Офлайн

Board footer

Модераторировать

Powered by DjangoBB

Lo-Fi Version