Python: сравнить dict со статической ссылкой? - PullRequest
0 голосов
/ 01 октября 2010

Я должен проверить, является ли словарь таким же, как он был вчера, если он изменился.

В PHP я мог бы сериализовать массив и сравнить полученные строки вчера и сегодня.Тем не менее, я не знаю, как это сделать в Py.Я немного читал о Pickle, и, может быть, это можно как-то сделать с md5?

Так что, в принципе, мне нужен способ разобрать dict в сопоставимое, хранимое значение, которое не является файлом и может быть жестко закодировано в.py файл.

Спасибо, AR

Ответы [ 6 ]

3 голосов
/ 01 октября 2010

Проблема со словарями заключается в их неопределенном порядке. Вы должны убедиться, что вы всегда получаете один и тот же результат из одинаковых словарей (если хотите сравнить их как строки).

Вы можете сделать это несколькими способами:

1) Хеш Python (только для проверки равенства; реализация хеша может быть специфичной для версии Python!)

print hash(str(sorted({1 : 2, 3 : 4}.items())))

2) MD5 (лучше всего, если вы хотите проверить равенство)

import hashlib
print hashlib.md5(str(sorted({1 : 2, 3 : 4}.items()))).hexdigest()

3) Травление (сериализация)

import pickle
serializedString = pickle.dumps({1 : 2, 3 : 4})

Модуль pickle имеет разные протоколы (и я думаю, что он не сортирует элементы словаря), поэтому вы не можете выполнять сравнение строк. Вы должны извлечь данные из словаря, а затем напрямую сравнить старый и новый словарь (d = pickle.loads(serializedString)).

4) Представление кортежа элемента (сериализация)

Согласно вашему комментарию, вы хотите что-то встраиваемое в исходный код Python. Как предложил С.Лотт, вы можете использовать объектное представление someDictionary.items(), представляющее собой список, содержащий все комбинации (ключ, значение) в виде кортежей (скорее всего, несортированных):

>>> repr({1 : 2, 3 : 4}.items())
'[(1, 2), (3, 4)]'

Вы можете скопировать и вставить это представление в ваш исходный код, если хотите, чтобы объект сериализовался как строка.

1 голос
/ 01 октября 2010

Вы можете использовать JSON, чтобы получить то, что вы просите.

from django.utils import simplejson as json

dict_1 = {'a': 1, 'b': 2, 'c': 3}
dict_2 = {'a': 2, 'b': 7, 'd': 9}

dict_1_str = json.dumps(dict_1, sort_keys=True)
dict_2_str = json.dumps(dict_2, sort_keys=True)

if dict_1_str == dict_2_str:
   # do something with the new dict...
   pass

Переменные dict_X_str будут содержать сериализованную версию dict.Вы можете сохранить его в memcahce или в хранилище данных для последующего сравнения.

0 голосов
/ 01 октября 2010

Если вы сделаете это, вы получите объект, который является последовательным и сопоставимым. Он имеет четко определенный и предсказуемый порядок. Вы можете использовать difflib, чтобы найти различия. Кроме того, вы можете легко восстановить из него высокопроизводительный словарь.

static = list(sorted(some_dict.items()))

a_dict= dict( static )
0 голосов
/ 01 октября 2010

Используя pickle, вы можете создать новый DictProperty, позволяющий поместить дикт в хранилище данных и получить его позже для сравнения.

Вот одна из реализаций: Можно ли сохранить словарь Python в хранилище данных Google BigTable без явной сериализации?

0 голосов
/ 01 октября 2010
pickle.dumps(set(yourdict.items()))
0 голосов
/ 01 октября 2010

pickle определенно то, что вы ищете.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...