![](/img/trans.png)
[英]Difference between Class Attributes, Instance Attributes, and Instance Methods in Python
[英]Can Instance Attributes Call Instance Class Methods in Python?
此处的Python noob尝试更多地使用类,并将我的代码分解为我正在使用的代码的更简单示例:
可以说我有一个类,带有一个实例和与该实例相关联的属性
class Foo(object):
def __init__(self, attribute=None):
self.attribute = attribute
def dosomething(self):
print('I did a thing!')
a = Foo()
a.attribute='bar'
现在,从实例“ a”运行方法可以按预期工作
a.dosomething()
出:
I did a thing!
但是,尝试从“ a”属性调用该方法会导致错误
a.attribute='bar'
a.attribute.dosomething()
AttributeError: 'str' object has no attribute 'dosomething'
这会导致属性错误,这是预期的。 “ a.attribute”不再是“ Foo”的类类型,而是“ str”的类类型。 我的问题是,我可以在类内部做一些事情以允许属性使用类方法吗?
此外,由于我在互联网搜索期间未找到任何结果,因此我假设不建议这样做,并且可能不是pythonic吗? (只是一个猜测)。 我愿意就如何使其更好地提出建议,但理想情况下,我希望保持属性不变,同时仍能够调用类方法。 类的属性的点语法确实可以帮助我使事情井井有条,但是如果不能调用其起源的类中的方法,这对我来说是无用的。
提前致谢!
不,这不起作用。 如果您了解类的工作原理,那确实没有任何意义。
该a.attribute
只是字符串'bar'
的名称。 该字符串不知道什么a
,也不应该。 1同一字符串可能还有许多其他名称。 例如:
>>> bar = 'bar'
>>> a.attribute = bar
>>> bar.dosomething()
AttributeError: 'str' object has no attribute 'dosomething'
那正是您所期望的,对吗? 但…
>>> a.attribute is bar
True
由于bar
与a.attribute
是同一对象,因此显然它必须做同样的事情:
>>> a.attribute.dosomething()
AttributeError: 'str' object has no attribute 'dosomething'
1,有一些特殊的情况下,这样的事情将是有益的,但他们是由具有属性不只是一个字符串,而是被某种智能对象的作品有点像一个字符串解决,但也知道它的类,实例或父级。 有关示例,请参见stdlib中的enum
模块,然后单击源代码链接以查看其实现方式。
在此示例中,当您执行a.attribute='bar'
时,属性为字符串,因此如果要执行type(a.attribute)
,它将返回string
。 因此,Python在str
类中寻找属性dosomething()
,但没有找到它。
您似乎想做的事情实际上没有任何意义。 猜测一下,似乎您将一些与继承相关的概念与对python的dot语法的理解混合在一起,以供成员参考,而这些概念彼此无关。
你写了
“ a.attribute”不再是“ Foo”的类类型,而是“ str”的类类型。
这表明对发生的事情有根本的误解。 任何国家都没有改变- a
依然实例a
,类型的Foo
。 它具有一个member attribute
,它是一个字符串。 表达a.attribute
仅仅指向该字符串。 如果您需要调用的方法a
,你仍然可以这样做任何你试图调用它a.attribute
:
>>> a.attribute = 'bar'
>>> a.doSomething()
I did a thing!
一种类型的对象调用其类中未定义的方法的常见情况是继承 :
class Foo(object):
def superclass_method(self):
print "Hi"
class Bar(Foo):
pass
b = Bar()
b.superclass_method() # prints "Hi"
在这种情况下,我们说b(也是Bar的实例) 也是 Foo。 因此,Foo定义的任何方法都可以访问Bar实例。
如果您告诉我们更多有关您要完成的工作的信息,那么我可以更具体地说明您是否以及如何使用继承。 但是,点符号只是谈论附加到对象的值的一种方法。 从字面上看,它只是在左侧对象的字典中查找与右侧名称相关联的值– foo.bar
等效于getattr(foo, 'bar')
。
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.