繁体   English   中英

__getattr__意外更新了非继承类的实例

[英]__getattr__ unexpectedly updates instance of a non-inherited class

我正在尝试针对车辆路径问题复制Java库的API,并着重强调了我对Python类不了解的一些知识。

车队可以分为两个基本标准: 第一种是您拥有的车辆类型(用于定义容量,运行成本等的VehicleType实例)和单个车辆(具有不同变速模式的Vehicle等)。

在我的简化示例中,我想定义一个VehicleType ,然后定义一个Vehicle ,它采用传递给构造函数的VehicleType的属性。 继伦纳特答案在这里 ,使用__getattr__在一般情况下完美的作品。 但是,想象一下,我有50名货车中的一名司机具有特殊资格来搬运危险物品,因此我想在Vehicle实例上添加一个额外的容量属性。 我尝试了以下方法:

class VehicleType(object):

    def __init__(self, fixed_cost=0, cost_per_distance=0, cost_per_time=0):
        self.capacities = {}
        self.fixed_cost = fixed_cost
        self.cost_per_distance = cost_per_distance
        self.cost_per_time = cost_per_time

    def add_capacity_dimension(self, dimension_id, dimension_size):
        """ Define a package type and how many of them this vehicle type can carry """
        self.capacities[dimension_id] = dimension_size


class Vehicle(object):

    def __init__(self, vehicle_type=None, identifier=None):
        self._vehicle_type = vehicle_type
        self.identifier = identifier

    def add_capacity_dimension(self, dimension_id, dimension_size):
        self.capacities[dimension_id] = dimension_size

    def __getattr__(self, name):
        return getattr(self._vehicle_type, name) 


if __name__ == '__main__':
    van_type = VehicleType()
    van_type.add_capacity_dimension("general items", 34)

    special_van = Vehicle(vehicle_type=van_type)
    special_van.add_capacity_dimension("hazardous chemicals", 50)

    print("Capacities of special van: {}".format(special_van.capacities))
    print("Capacity of van_type:      {}".format(van_type.capacities)) # Why?

我不明白为什么我的做法也影响了capacities的的van_type Vehicle不能直接从VehicleType继承,而我已经在Vehicle类中定义了add_capacity_dimension 这也与我对有关__getattr__ 的文档的理解相矛盾:

当在常规位置未找到属性时调用该属性(即,它不是实例属性,也不是在自身的类树中找到该属性)。 name是属性名称。

有人可以解释为什么实例van_type在这里也受到影响吗?

Vehicle实例没有“容量”属性。

通过自定义__getattr__ ,对special_van上的self.capacities属性查找(来自Vehicle.add_capacity_dimension实现)不是在Vehicle而是在VehicleType上解析的。

因此, special_van.capacitiesvan_type.capacities是相同的字典。

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM