在 Python 中使用数据类方法定义属性
Define an attribute with a dataclass method in Python
我有一个 class 用于边界框坐标,我想将其转换为数据 class,但我不知道如何使用 class 方法设置属性,例如我会在一个正常的 class。这是正常的 class:
class BBoxCoords:
"""Class for bounding box coordinates"""
def __init__(self, top_left_x: float, top_left_y: float, bottom_right_x: float, bottom_right_y: float):
self.top_left_x = top_left_x
self.top_left_y = top_left_y
self.bottom_right_x = bottom_right_x
self.bottom_right_y = bottom_right_y
self.height = self.get_height()
def get_height(self) -> float:
return self.bottom_right_y - self.top_left_y
这是我想要它做的:
bb = BBoxCoords(1, 1, 5, 5)
bb.height
> 4
这正是我想要的。我试图用 dataclass
做同样的事情
from dataclasses import dataclass
@dataclass
class BBoxCoords:
"""Class for bounding box coordinates"""
top_left_x: float
top_left_y: float
bottom_right_x: float
bottom_right_y: float
height = self.get_height()
def get_height(self) -> float:
return self.bottom_right_y - self.top_left_y
但是当我尝试使用它时 self
没有定义,所以我得到一个 NameError。使用数据 class 执行此操作的正确方法是什么?我知道我可以做到
bb = BBoxCoords(1, 1, 5, 5)
bb.get_height()
> 4
但我宁愿调用属性而不是方法。
对于这种事情,您需要 __post_init__
,这将 运行 在 __init__
之后。另外,请确保 height
未在 __init__
中设置,因此:
from dataclasses import dataclass, field
@dataclass
class BBoxCoords:
"""Class for bounding box coordinates"""
top_left_x: float
top_left_y: float
bottom_right_x: float
bottom_right_y: float
height: float = field(init=False)
def __post_init__(self):
self.height = self.get_height()
def get_height(self) -> float:
return self.bottom_right_y - self.top_left_y
进行中:
In [1]: from dataclasses import dataclass, field
...:
...: @dataclass
...: class BBoxCoords:
...: """Class for bounding box coordinates"""
...: top_left_x: float
...: top_left_y: float
...: bottom_right_x: float
...: bottom_right_y: float
...: height: float = field(init=False)
...:
...: def __post_init__(self):
...: self.height = self.get_height()
...:
...: def get_height(self) -> float:
...: return self.bottom_right_y - self.top_left_y
...:
In [2]: BBoxCoords(1, 1, 5, 5)
Out[2]: BBoxCoords(top_left_x=1, top_left_y=1, bottom_right_x=5, bottom_right_y=5, height=4)
我有一个 class 用于边界框坐标,我想将其转换为数据 class,但我不知道如何使用 class 方法设置属性,例如我会在一个正常的 class。这是正常的 class:
class BBoxCoords:
"""Class for bounding box coordinates"""
def __init__(self, top_left_x: float, top_left_y: float, bottom_right_x: float, bottom_right_y: float):
self.top_left_x = top_left_x
self.top_left_y = top_left_y
self.bottom_right_x = bottom_right_x
self.bottom_right_y = bottom_right_y
self.height = self.get_height()
def get_height(self) -> float:
return self.bottom_right_y - self.top_left_y
这是我想要它做的:
bb = BBoxCoords(1, 1, 5, 5)
bb.height
> 4
这正是我想要的。我试图用 dataclass
做同样的事情from dataclasses import dataclass
@dataclass
class BBoxCoords:
"""Class for bounding box coordinates"""
top_left_x: float
top_left_y: float
bottom_right_x: float
bottom_right_y: float
height = self.get_height()
def get_height(self) -> float:
return self.bottom_right_y - self.top_left_y
但是当我尝试使用它时 self
没有定义,所以我得到一个 NameError。使用数据 class 执行此操作的正确方法是什么?我知道我可以做到
bb = BBoxCoords(1, 1, 5, 5)
bb.get_height()
> 4
但我宁愿调用属性而不是方法。
对于这种事情,您需要 __post_init__
,这将 运行 在 __init__
之后。另外,请确保 height
未在 __init__
中设置,因此:
from dataclasses import dataclass, field
@dataclass
class BBoxCoords:
"""Class for bounding box coordinates"""
top_left_x: float
top_left_y: float
bottom_right_x: float
bottom_right_y: float
height: float = field(init=False)
def __post_init__(self):
self.height = self.get_height()
def get_height(self) -> float:
return self.bottom_right_y - self.top_left_y
进行中:
In [1]: from dataclasses import dataclass, field
...:
...: @dataclass
...: class BBoxCoords:
...: """Class for bounding box coordinates"""
...: top_left_x: float
...: top_left_y: float
...: bottom_right_x: float
...: bottom_right_y: float
...: height: float = field(init=False)
...:
...: def __post_init__(self):
...: self.height = self.get_height()
...:
...: def get_height(self) -> float:
...: return self.bottom_right_y - self.top_left_y
...:
In [2]: BBoxCoords(1, 1, 5, 5)
Out[2]: BBoxCoords(top_left_x=1, top_left_y=1, bottom_right_x=5, bottom_right_y=5, height=4)