Найти - Пользователи
Полная версия: аналог ассоциативных массивов
Начало » Python для новичков » аналог ассоциативных массивов
1 2
atomAltera
Вот как я решил аналогичную задачу, сортировка по первой букве

N = ("print", "for", "if", "is", 
"try", "in", "sorted", "type", "range", "str",
"pow", "len", "locals", "hash", "tuple");


D = {k: sorted([v for v in N if v[0].lower() == k]) for k in sorted(k[0].lower() for k in N)};

for k in D.keys():
print('-', k.upper(), '-', len(D[k]));
for v in D[k]:
print(v);
print();
Не знаю правда на сколько он быстрый
Isem
Второй sorted не имеет смысла, так как словарь в питоне не упорядочен.
То есть вот так:
D = {k:sorted(v for v in N if v[0]==k) for k in set(ch[0] for ch in N)}
Ну а если для скорости (когда список N большой), то можно так:
from collections import defaultdict
D = defaultdict(list)
for k in N: D[k[0]].append( k )
for l in D.values(): l.sort()
py.user.next
atomAltera
Не знаю правда на сколько он быстрый
D = {k: sorted([v for v in N if v[0].lower() == k]) for k in sorted(k[0].lower() for k in N)};
пересоздаются списки
например, для слов if и is будет составляться один и тот же список
atomAltera
py.user.next
atomAltera
Не знаю правда на сколько он быстрый
D = {k: sorted([v for v in N if v[0].lower() == k]) for k in sorted(k[0].lower() for k in N)};
пересоздаются списки
например, для слов if и is будет составляться один и тот же список
По-моему это происходит следующим образом:
N = ("print", "for", "if", "is", 
"try", "in", "sorted", "type", "range", "str",
"pow", "len", "locals", "hash", "tuple")


#D = {k: sorted([v for v in N if v[0].lower() == k]) for k in (k[0].lower() for k in N)}
keys = tuple(k[0] for k in N)
D = {k: [v for v in N if v[0] == k] for k in keys}

for k in D.keys():
print(k, '-', len(D[k]))
for v in D[k]:
print(v)
print()
Сначала создаётся список ключей keys, а потом словарь D, для которого ключ берётся из keys а значение - список (ну можно и картедж) тех элементов в исходном списке которые попадают пот ключ k.
В коде исходное выражение закоментированно и заменено на 2 следующих.
А в чём проблема собственно? Как оптимизировать, ну разве что заменить списки на кортеджи?

D = {k: tuple(v for v in N if v[0].lower() == k) for k in tuple(k[0].lower() for k in N)}
py.user.next
не кортеджи, а кортежи
http://ru.wikipedia.org/wiki/%D0%9A%D0%BE%D1%80%D1%82%D0%B5%D0%B6

кортежи сохраняют одинаковые элементы
>>> N = ("print", "for", "if", "is", 
... "try", "in", "sorted", "type", "range", "str",
... "pow", "len", "locals", "hash", "tuple")
>>> t = tuple(k[0].lower() for k in N)
>>> t
('p', 'f', 'i', 'i', 't', 'i', 's', 't', 'r', 's', 'p', 'l', 'l', 'h', 't')
>>>
для кажого элемента ‘i’ будет снова создаваться один и тот же список
это пересоздание одного и того же списка несколько раз

{k: sorted([v for v in N if v[0].lower() == k])
вот эта часть будет несколько раз сортировать одно и то же
atomAltera
Ясно, значит надо множества использовать?
D = {k: tuple(v for v in N if v[0].lower() == k) for k in set(k[0].lower() for k in N)}
This is a "lo-fi" version of our main content. To view the full version with more information, formatting and images, please click here.
Powered by DjangoBB