I am looking for fixed keys, like a namedtuple
, but mutable values like a dict
. I would probably have used a struct
in C. Is there such a data structure in Python?
Asked
Active
Viewed 428 times
0

Thomas Arildsen
- 1,079
- 2
- 14
- 31
-
Just write a custom class. For a simple, "record-like" type, you can use the `dataclasses.dataclass` code generator to avoid boilerplate – juanpa.arrivillaga Dec 16 '21 at 21:50
-
It is important to understand, Python is a *purely object oriented language* (and no, Java fans, that doesn't mean that everything is a class definition!). So, when you think of a C struct definition , you probably want some sort of class definition. Note, `namedtuple` is just a *class factory*. It generates a new type, a subclass of `tuple` – juanpa.arrivillaga Dec 16 '21 at 21:54
2 Answers
5
You may use a dataclass.
Dataclasses are close to mutable namedtuples. They're not a tuple, but I believe they will satisfy your needs.

Bharel
- 23,672
- 5
- 40
- 80
-
It is important to note, a data class isnt a *type of object*, that is a decorator which generates code to avoid boilerplate. But yeah, this is probably a good solution for the OP – juanpa.arrivillaga Dec 16 '21 at 21:50
-
@juanpa.arrivillaga while it's technically true, it's much more than a simple decorator, considering there is even a check for [is_dataclass](https://docs.python.org/3/library/dataclasses.html#dataclasses.is_dataclass), so I will tend to disagree with the statement that it isn't a type of an object, as much as an iterator isn't technically a type but rather a protocol. – Bharel Dec 16 '21 at 21:53
-
Well, no. All that does is check if the type of object you passed in has the attribute `__dataclass_fields__`. Like, go ahead and define `class Foo: pass` then `Foo.__dataclass_fields__ = None` then check `is_dataclass(Foo())` – juanpa.arrivillaga Dec 16 '21 at 21:57
-
Note, while this sounds nitpicky, I think it is an important thing to keep in mind. I up voted, for the record – juanpa.arrivillaga Dec 16 '21 at 22:00
-
@juanpa.arrivillaga and all `isinstance(a, collections.abc.Iterator)` does is check `__iter__` and `__next__`. Does that mean `a` isn't an iterator or that iterator isn't a type? – Bharel Dec 16 '21 at 22:00
-
yes it isn't a type. An iterator is any object that implements the iterator protocol. Understanding what a type is is important. It is basically one of the central aspects of the language – juanpa.arrivillaga Dec 16 '21 at 22:01
-
@juanpa.arrivillaga it is a little nitpicky, as when people say a certain class is a type of something, they can mean it inherits from, it implements a certain interface, it implements a certain protocol. They don't necessarily mean it inherits from a specific class. A list is a type of a container. – Bharel Dec 16 '21 at 22:01
-
1For sure, I understand what you are saying. Python is very much a language that embraces "duck typing" anyway. But this is programming, it is hard to be *too* pedantic. ;) And I just want to be precise for someone coming from a language like C, which is weakly typed, indeed, types are basically something the compiler sees. – juanpa.arrivillaga Dec 16 '21 at 22:03
-
`dataclass` does look useful. When I take https://stackoverflow.com/a/45426493/865169 for a quick spin, I get a `Point` `p` where I can still say `p.a = 1`. Although `p` does not immediately show me the property `a` when I display it (only `x`, `y`, and `z`), it is still there; I can get it as `p.a`. The ability to just add additional properties/keys at will is kind of what I was trying to avoid. Is there no property-/key-wise immutable solution? – Thomas Arildsen Dec 17 '21 at 22:26
-
1
-
1
Check the dataclass decorator:
https://docs.python.org/3/library/dataclasses.html#dataclasses.asdict
from dataclasses import dataclass
@dataclass
class Point:
x: int
y: int
p = Point(10,20)
# or: Point(x=10, y=20)
print(p)
# Output: Point(x=10, y=20)
print(p.x)
# Output: 10

albert
- 4,290
- 1
- 21
- 42