【问题标题】:Why overidding is required for a dict class in Python为什么 Python 中的元类需要覆盖
【发布时间】:2016-01-10 01:33:24
【问题描述】:

我正在阅读banking application 的源代码,bank 类定义如下:

class Bank(object):
    """ the bank class contains all the bank operations """

    def __init__(self, name):
        """ instantiate the class """
        self.name = str(name)
        self.customers = Customers()

现在self.customersCustomers 类的另一个实例,定义如下:

class Customers(dict):
    """ the customers class extends the dictionary object """

    def __setitem__(self, key, item):
        self.__dict__[key] = item

    def __getitem__(self, key):
        return self.__dict__[key]

    def __repr__(self):
        return repr(self.__dict__)

    def __len__(self):
        return len(self.__dict__)

    def __delitem__(self, key):
        del self.__dict__[key]

    def keys(self):
        return self.__dict__.keys()

    def values(self):
        return self.__dict__.values()

    def __cmp__(self, dict):
        return cmp(self.__dict__, dict)

    def __contains__(self, item):
        return item in self.__dict__

    def add(self, key, value):
        self.__dict__[key] = value

    def __iter__(self):
        return iter(self.__dict__)

    def __call__(self):
        return self.__dict__

    def __unicode__(self):
        return unicode(repr(self.__dict__))
  • 根据我的理解,我们override a function 在添加新功能或其行为从以前的功能更改时。为什么我们是overridingdictCustomer 类中的函数。我们不能简单地使用 self.customers = dict() 吗?因为我们没有在此处添加任何新内容。

【问题讨论】:

  • 这段代码很糟糕,毫无意义,而且有问题。它实际上是两个 dicts,selfself.__dict__,并且由于只有一些dict 方法被覆盖,一些方法看不到其他方法的操作的效果。例如the Bank class tries to call get and pop,没有被覆盖,所以添加后找不到客户。 __repr__ 具有误导性,__call__ 很奇怪,总的来说,这只是糟糕的代码。
  • 你能帮我改进一下吗?我还在Python 中编写银行应用程序,希望能得到您的帮助。
  • 完全忽略此代码。对于字典,只需使用常规字典而不对其进行子类化。对于银行代码的其余部分,您可以独立于该代码的功能做出自己的设计决策。这段代码不是一个有用的起点。

标签: python class oop inheritance dictionary


【解决方案1】:

课程不仅仅是dict;它也支持键的属性访问,因为它将所有字典访问委托给实例__dict__ 属性,该属性包含所有属性。

演示:

>>> c = Customers()
>>> c.foo = 'bar'
>>> c
{'foo': 'bar'}
>>> c['foo']
'bar'

普通字典无法做到这一点。您找到的实现是这个问题答案的一个相当复杂的版本:Accessing dict keys like an attribute in Python?

【讨论】:

  • @python:自定义类的实例将您设置的属性存储在__dict__ 属性中。 dict 的这个子类将所有对键的访问重定向到 __dict__ 属性,因此设置键实际上是设置属性。
  • 不,不是,请参阅链接的问题。
  • 这个类的实现方式,也不需要继承dict
  • 您做出了一个有问题的假设,即支持属性访问是一个设计目标,而不是作者不知道自己在做什么的巧合效应。此代码来自的项目实际上并未使用属性访问。 It does use get and pop,尽管没有覆盖它们,所以它最终混合了对 __dict__ 属性和继承的 dict 结构的访问,并且它没有找到它添加的任何条目。
  • @user2357112: 是的,鉴于所呈现的类是dict 的子类化,而实际上并没有正确地做到这一点,因此犯了更多错误并不让我感到惊讶。单独来看,它看起来像是在尝试制作一个也支持属性访问的字典。
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2017-11-17
  • 1970-01-01
  • 2010-09-23
相关资源
最近更新 更多