Уведомления

Группа в Telegram: @pythonsu

#1 Сен. 1, 2007 21:43:37

umup
От:
Зарегистрирован: 2007-07-14
Сообщения: 53
Репутация: +  0  -
Профиль   Отправить e-mail  

как отключить сортировку dict-а ?

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



Офлайн

#2 Сен. 1, 2007 22:40:09

nss
От:
Зарегистрирован: 2007-01-06
Сообщения: 103
Репутация: +  0  -
Профиль   Отправить e-mail  

как отключить сортировку dict-а ?

Нет, нельзя. Dict это бинарное дерево.

Можно сделать свой тип с методами __getitem__ и __setitem__, с которым можно будет работать как с обычным dict'ом. Но он будет гораздо медленнее.



Офлайн

#3 Сен. 1, 2007 23:05:18

umup
От:
Зарегистрирован: 2007-07-14
Сообщения: 53
Репутация: +  0  -
Профиль   Отправить e-mail  

как отключить сортировку dict-а ?

nss
Нет, нельзя. Dict это бинарное дерево.
Можно сделать свой тип с методами __getitem__ и __setitem__, с которым можно будет работать как с обычным dict'ом. Но он будет гораздо медленнее.
мда… плохо.
значить придется через list dictов, но поиск по текстовым полям будет медленный.



Офлайн

#4 Сен. 1, 2007 23:10:24

umup
От:
Зарегистрирован: 2007-07-14
Сообщения: 53
Репутация: +  0  -
Профиль   Отправить e-mail  

как отключить сортировку dict-а ?

хотя.. сделаю для каждого dictа свой list с ключами, отсортированными в нужном порядке.



Офлайн

#5 Сен. 1, 2007 23:28:14

Андрей Светлов
От:
Зарегистрирован: 2007-05-15
Сообщения: 3137
Репутация: +  14  -
Профиль   Адрес электронной почты  

как отключить сортировку dict-а ?

Это пример из sqlalchemy

sqlalchemy.utils


class OrderedDict(dict):
“”“A Dictionary that returns keys/values/items in the order they were added.”“”

def __init__(self, ____sequence=None, **kwargs):
self._list =
if ____sequence is None:
self.update(**kwargs)
else:
self.update(____sequence, **kwargs)

def clear(self):
self._list =
dict.clear(self)

def update(self, ____sequence=None, **kwargs):
if ____sequence is not None:
if hasattr(____sequence, ‘keys’):
for key in ____sequence.keys():
self.__setitem__(key, ____sequence)
else:
for key, value in ____sequence:
self = value
if kwargs:
self.update(kwargs)

def setdefault(self, key, value):
if key not in self:
self.__setitem__(key, value)
return value
else:
return self.__getitem__(key)

def __iter__(self):
return iter(self._list)

def values(self):
return [self for key in self._list]

def itervalues(self):
return iter(self.values())

def keys(self):
return list(self._list)

def iterkeys(self):
return iter(self.keys())

def items(self):
return [(key, self) for key in self.keys()]

def iteritems(self):
return iter(self.items())

def __setitem__(self, key, object):
if key not in self:
self._list.append(key)
dict.__setitem__(self, key, object)

def __delitem__(self, key):
dict.__delitem__(self, key)
self._list.remove(key)

def pop(self, key):
value = dict.pop(self, key)
self._list.remove(key)
return value

def popitem(self):
item = dict.popitem(self)
self._list.remove(item)
return item



Кажется, то, что нужно. Незачем кодить самому.
Можно просто взять готовое. То, что хотел - ну уже реализованное.
Свой порядок легко сюда вставить. Если в self._list добавлять и удалять через bisect - получишь dict, упорядоченный по твоим правилам.
Заметь, __getitem__ не перегружается - т.е. поиск по ключу быстр так же, как и в dict.

Если keys/iterkeys, values/itervalues, items/iteritems переставить - сначала генератор, а только потом из него список - выйдет еще быстрее.
Вроде того:

def values(self):
return list(self.itervalues())

def itervalues(self):
return (self for key in self._list)

def keys(self):
return list(self.iterkeys())

def iterkeys(self):
return iter(self._list)

def items(self):
return self.iteritems()

def iteritems(self):
return ((key, self) for key in self.iterkeys())



Отредактировано (Сен. 2, 2007 00:01:08)

Офлайн

Board footer

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

Powered by DjangoBB

Lo-Fi Version