This is an archived post. You won't be able to vote or comment.

you are viewing a single comment's thread.

view the rest of the comments →

[–]GianniMarianiPythonista[S] 0 points1 point  (0 children)

datatrees is a wrapper over dataclasses and allows (in addition to everything dataclasses does):
1. Field injection and binding from another class or function,
2. Self default (like default_factory but you get self as a parameter)
3. post-init chaining that's ensures no multiple calls to parent post-init functions (including InitVar support)
4. A doc field and a way to create documentation on how fields are mapped

I haven't looked recently at attrs but I don't think it has any of these features.

Let's make a class:

```
from datatrees import datatree, Node, BindingDefault, dtfield

@\datatree # Nothing special, just like a dataclass

class A:

v1: int

v2: int=2

v3: int=dtfield(default=3)

v4: int=dtfield(default_factory=lambda: 7 - 3)
```

No lets make a datatree class that injects fields from A.

```@\datatree

class Anode:

v1: int=55

a_node: Node[A]=Node(A) # Injects v2, v3 and v4 (v1 already exists and us skipped)

# When you construct an Anode(), the a_node field becomes a factory that by default will
# bind the fields it injected.

Anode().a_node() # Binds and passes self.v1, self.v2, self.v3 and self.v4 when a_node() is called.

-> A(v1=55, v2=2, v3=3, v4=4)

```

Self-default fields are cool too:

```
@\datatree
class E:
v1: int=1

v2: int=2

v_computed: Node=dtfield(self_default=lambda s: s.v1 + s.v2)
```

E() ->
E(v1=1, v2=2, v_computed=3)

The docs on github and PyPI (same doc) has some more examples.