Pour créer la sous-classe, il suffit de passer directement les clés d'un dict :
MyTuple = namedtuple('MyTuple', d)
Il s'agit maintenant de créer des instances de tuple à partir de ce dict, ou de tout autre dict dont les clés correspondent :
my_tuple = MyTuple(**d)
Attention : Comparaison de n-uplets nommés sur valeurs uniquement (commandés). Ils sont conçus pour remplacer directement les tuples ordinaires, avec l'accès aux attributs nommés comme caractéristique supplémentaire. Les noms des champs ne sont pas pris en compte lors des comparaisons d'égalité. . Il se peut que ce ne soit pas ce que vous vouliez ou attendiez de l namedtuple
type ! Cela diffère de dict
les comparaisons d'égalité, qui prennent en compte les clés et ne tiennent pas compte de l'ordre des comparaisons.
Pour les lecteurs qui n'ont pas vraiment besoin d'un type qui soit une sous-classe de tuple il n'y a probablement pas beaucoup d'intérêt à utiliser un namedtuple en premier lieu. Si vous souhaitez simplement utiliser la syntaxe d'accès aux attributs sur les champs, il serait plus simple et plus facile de créer espace de noms à la place :
>>> from types import SimpleNamespace
>>> SimpleNamespace(**d)
namespace(a=1, b=2, c=3, d=4)
La raison pour laquelle je veux convertir mon dictionnaire en namedtuple est qu'il devient hachable, mais reste généralement utilisable comme un dict.
Pour une recette de type "attrdict" pouvant être hachée, consultez un fichier congelé boîte :
>>> from box import Box
>>> b = Box(d, frozen_box=True)
>>> hash(b)
7686694140185755210
>>> b.a
1
>>> b["a"]
1
>>> b["a"] = 2
BoxError: Box is frozen
Il est également possible qu'un type de mappage gelé soit proposé dans une version ultérieure de Python ; surveillez ce projet de PEP pour savoir s'il est accepté ou rejeté :
PEP 603 -- Ajout d'un type frozenmap aux collections
0 votes
D'après la documentation, il n'y a pas de chemin plus court. Cependant, vous pourriez étendre la classe et implémenter la méthode.
0 votes
Avec les namedtuples, vous êtes censé créer le type namedtuple une fois et l'utiliser à plusieurs reprises, et non générer un nouveau type namedtuple à chaque fois. Générer un nouveau type de namedtuple à chaque fois est lent et va à l'encontre de tout avantage en termes d'espace.
1 votes
@user2357112 vraisemblablement, l'utilisateur a plusieurs dicts avec les mêmes clés.
2 votes
Il n'y aura pas de module intégré qui construira le type et le tuple en même temps, parce que vous êtes censé réutiliser le type.
0 votes
Tout à fait d'accord avec @user2357112. Définir un tuple nommé à partir d'un dictionnaire se fait en une ligne, nt= namedTupleConstructor(**d). La première ligne est la définition d'une nouvelle classe, qui est censée être réutilisée.
0 votes
Pour aller dans l'autre sens (namedtuple dans le dictionnaire), voir ici : stackoverflow.com/q/26180528/674039