这样的事情总是描述性的!每个B 都有一个A 对象吗?如果是这样,那么你最好使用#1。 B 是某种容器,在这种情况下有一个 A 对象吗?使用#2。
例如,假设我正在构建Tile 对象的地图。每个Tile 对象都有一个location,我将其进一步抽象为Location 对象,如下所示:
class Tile(object):
def __init__(self, location, *args, **kwargs):
self.location = location
class Location(object):
def __init__(self, x, y):
self.x = x
self.y = y
x2_y3 = Location(2, 3)
tile = Tile(x2_y3)
tile.location.x # 2
现在我也可以这样做:
class Tile(object):
def __init__(self, location: "(x, y)", *args, **kwargs):
x, y = location
self.location = Location(x, y)
class Location(object):
def __init__(self, x, y):
self.x = x
self.y = y
tile = Tile(2,3) # builds its own location object
在这种情况下,第二种策略可能更可取,但我更喜欢第一种,因为它更易于扩展。如果以后我转移到 3D 空间,我可以这样做:
class Location3D(Location):
def __init__(self, x, y, z):
self.z = z
super().__init__(x, y)
tile = Tile(Location3D(2, 3, -1))
在第二种策略中,这将失败,因为Tiles 总是有Location 对象。您必须对 Tile 进行猴子补丁才能使其正常工作,或者构建一个新的 Tile3D 对象,该对象可能与其他 Tiles 配合得很好,也可能不适合。