2010-11-17 31 views
5

[Python 3.1]Python: comment créer un hachage de conteneurs imbriqués

Je suis en train de créer un hachage pour un conteneur qui peut avoir des conteneurs imbriqués en elle, avec une profondeur inconnue. À tous les niveaux de la hiérarchie, il n'y a que des types intégrés. Quel est un bon moyen de faire ça?

Pourquoi je besoin:

Je cache le résultat de certains calculs dans un objet de conserves au vinaigre (sur le disque). Je devrais invalider ce fichier mis en cache si la fonction est appelée avec des paramètres différents (cela arrive rarement, donc je ne vais pas enregistrer plus d'un fichier sur le disque). Le hachage sera utilisé pour comparer les paramètres.

+0

Attendez-vous à ce que ces valeurs puissent changer après les avoir créées? – aaronasterling

+0

@aaronsterling: Pouvez-vous clarifier s'il vous plaît? Je ne suis pas sûr de répondre à votre question, mais les conteneurs ou leur contenu ne seront pas modifiés. Cependant, je dois souligner que la persistance est, bien sûr, requise pour toute invocation future de ce programme Python (dans un nouveau processus). – max

+0

Vous êtes donc OK avec une petite chance que le fichier ne soit pas invalidé par des paramètres de fonction différents? Toute fonction de hachage aura une chance de collision, donc vous en recherchez une avec une chance de collision minimale. J'essaie juste de comprendre un peu mieux le problème. –

Répondre

1

Vous pourriez juste sérialiser les paramètres dans quelque chose comme JSON, et l'utiliser pour le hachage.

+0

J'aime cette idée. Y a-t-il des problèmes cachés avec ça? Par exemple, est-ce qu'il casserait certaines structures de nidification compliquées, etc.? – max

+0

Non, tant que ce ne sont que des tuples, des listes, des dicts, des strs et des ints, ça vous va. Une mise en garde, cependant: 'tuple' ==' list' (comme JavaScript n'a pas de concept 'tuple') –

+2

Je pense que j'utiliserais' pickle.dumps' au lieu de 'json.dumps'; le cornichon est précis avec les types et ~ 15% plus rapide (je les ai chronométrés). –

1

Si tous les conteneurs sont des tuples et que tous les objets contenus sont lavables, le conteneur principal doit être lavable.

+0

Bon point. Malheureusement, parmi les conteneurs sont des dictionnaires. – max

+1

Vous pouvez convertir des dictionnaires en un tuple trié de tuples (clé, valeur). – Paul

0

Je le ferais avec json sérialisation comme une chaîne [et puis hachage cette chaîne si c'est toujours nécessaire].

from simplejson import dumps 

def hash_data(data): 
    return hash(dumps(data))