Dataclasses
Many classes just hold data: a Point, a Product, a Student. Writing __init__, __repr__ and __eq__ by hand for each is repetitive. The @dataclass decorator writes them for you.
Before and after
By hand:
Python
class Product:
def __init__(self, name, price, stock):
self.name = name
self.price = price
self.stock = stock
def __repr__(self):
return f"Product(name={self.name!r}, price={self.price}, stock={self.stock})"
def __eq__(self, other):
return (self.name, self.price, self.stock) == (other.name, other.price, other.stock)
print(Product("Lamp", 27.75, 48))With a dataclass:
Python
from dataclasses import dataclass
@dataclass
class Product:
name: str
price: float
stock: int
lamp = Product("Lamp", 27.75, 48)
print(lamp)
print(lamp == Product("Lamp", 27.75, 48))
print(lamp.price)You list the fields with type hints (name: str), and __init__, __repr__ and __eq__ are generated.
Default values
Python
from dataclasses import dataclass
@dataclass
class Task:
title: str
priority: int = 3
done: bool = False
print(Task("Write tests"))
print(Task("Fix bug", priority=1))Fields with defaults must come after fields without them.
Mutable defaults need field()
A list default would be shared by every instance (the same trap as with functions), so dataclasses refuse it. Use field(default_factory=...):
Python
from dataclasses import dataclass, field
@dataclass
class Course:
name: str
lessons: list = field(default_factory=list)
py = Course("Python")
js = Course("JavaScript")
py.lessons.append("Intro")
print(py, js)Methods still work
Python
from dataclasses import dataclass
@dataclass
class Rectangle:
width: float
height: float
def area(self):
return self.width * self.height
print(Rectangle(3, 4).area())Frozen and ordered dataclasses
frozen=True makes instances immutable (and usable as dictionary keys); order=True adds <, > and friends, comparing fields in order:
Python
from dataclasses import dataclass
@dataclass(frozen=True, order=True)
class Version:
major: int
minor: int
patch: int = 0
versions = [Version(1, 10), Version(1, 2, 5), Version(0, 9)]
print(sorted(versions))
print(max(versions))
v = Version(2, 0)
v.major = 3Finished this lesson?Mark it complete to earn +20 XP and move your progress on.