【问题标题】:if a property sample work如果一个属性样本工作
【发布时间】:2015-07-23 00:42:21
【问题描述】:

在《Core Python Programming》一书中,有一个关于如何使用属性的示例。代码是这样的:

class Hidex(object):
    def __init__(self, x):
        self.__x = x
    @property
    def x():
        def fget(self):
            return ~self.__x
        def fset(self, x):
            assert isinstance(val, int), 'val must be int'
            self.__x = ~x
        return locals()

书上说,这个类将使用以下代码:

inst = Hidex(20)
print inst.x
inst.x = 30
print inst.x

但我认为这门课不会奏效。因为在访问inst.x时,解释器实际上会运行Hidex.__dict__['x'].__get__(x, Hidex),并且因为x = property(x),所以property的第一个arg'fget'是x,而不是x()中定义的函数'fget'。

另外,当我运行这段代码时,我得到了以下结果:

{'fget': <function fset at 0x.....>, 'self': <__main__.xxxx>, 'fget': <function fget at 0x....>}
traceback:
...... # this result is just telling t.x = 30 cannot run, just skip the details
AttributeError: cannot set attribute

我错过了什么吗?为什么这本书打算这样做?

【问题讨论】:

  • this code doesn't work either. - 请解释实际问题。为什么你认为代码不能正常工作?
  • 嗨@thefourtheye,我更新了问题。你认为我们可以像这样使用属性吗?

标签: python properties descriptor


【解决方案1】:

这是有道理的:

class Hidex(object):

    def __init__(self, x):
        self.__x = x

    @property
    def x(self):
            return ~self.__x

    @x.setter
    def x(self, x):
        assert isinstance(x, int), 'val must be int'
        self.__x = ~x

看起来您问题代码中的@property 不是内置的,而是不同的版本。

这可能是这里的意图:

def nested_property(func):
    """Make defining properties simpler.
    """
    names = func()
    names['doc'] = func.__doc__
    return property(**names)


class Hidex(object):
    def __init__(self, x):
        self.__x = x
    @nested_property
    def x():
        def fget(self):
            return ~self.__x
        def fset(self, x):
            assert isinstance(x, int), 'val must be int'
            self.__x = ~x
        return locals()

【讨论】:

  • 非常感谢@Mike Müller,我知道这会奏效。我的问题是,这本书坚持上面的代码有效,但我不这么认为。而且我不确定我是否错过了什么。
  • 这可能是问题所在。如果这是真的,那么看起来这本书需要更新
  • @Spybdai 是的。还有另一个复制粘贴问题。它说assert isinstance(val, int),但它必须是x 而不是val。猜猜看,本书代码示例需要进行单元测试。
猜你喜欢
  • 2013-04-03
  • 2015-04-01
  • 1970-01-01
  • 1970-01-01
  • 2014-02-22
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多