Python类中'cls'和'self'之间的区别?

Posted

技术标签:

【中文标题】Python类中\'cls\'和\'self\'之间的区别?【英文标题】:Difference between 'cls' and 'self' in Python classes?Python类中'cls'和'self'之间的区别? 【发布时间】:2011-06-04 12:31:48 【问题描述】:

为什么有时在 Python 类中使用 cls 而不是 self 作为参数?

例如:

class Person:
    def __init__(self, firstname, lastname):
        self.firstname = firstname
        self.lastname = lastname

    @classmethod
    def from_fullname(cls, fullname):
        cls.firstname, cls.lastname = fullname.split(' ', 1)

【问题讨论】:

【参考方案1】:

如果要通过实例访问方法,请将第一个参数保留为 self。例如:

class Test:
   def hello(self, name):
      print ('hello ', name)

obj = Test()
obj.hello('Rahul')

如果你想像我们在静态类中那样使用类名访问方法,最好使用 cls 作为方法中的第一个参数。例如:

class Test:
       def hello(cls, name):
          print ('hello ', name)


Test.hello('Rahul')

【讨论】:

【参考方案2】:

"self""cls" 之间的区别在 PEP 8 中定义。正如 Adrien 所说,这不是强制性的。这是一种编码风格。 PEP 8 说:

函数和方法参数

始终使用self 作为实例方法的第一个参数。

始终使用cls 作为类方法的第一个参数。

【讨论】:

【参考方案3】:

这是一个很好的问题,但不像问题那么需要。 'self' 和 'cls' 使用的方法是有区别的,虽然类似地它们在同一个地方

def moon(self, moon_name):
    self.MName = moon_name

#but here cls method its use is different 

@classmethod
def moon(cls, moon_name):
    instance = cls()
    instance.MName = moon_name

现在你可以看到两个都是moon函数,但是一个可以在类中使用,而另一个函数名moon可以用于任何类。

对于实用的编程方法:

在设计圆形类时,我们使用 area 方法作为 cls 而不是 self,因为我们不希望区域仅限于特定的圆形类。

【讨论】:

如果你想添加更多的东西,编码人员正在寻找,如果正确,将批准它。【参考方案4】:

类方法不接受 self 参数,而是接受一个 cls 参数,该参数指向 class——而不是 object 实例——当 该方法被调用。 由于类方法只能访问这个 cls 参数,它不能 修改对象实例状态。那将需要访问 self 。但是,类方法仍然可以修改适用于所有 类的实例。

-Python 技巧

【讨论】:

【参考方案5】:

cls 表示方法属于该类,而 self 表示该方法与该类的实例相关,因此带有 cls 的成员通过类名访问,而带有 self 的成员通过类的实例访问类...如果您来自java背景,它与java中的static membernon-static members的概念相同。

【讨论】:

感谢Java参考,现在明白了。 谢谢你提到static membernon-static members,在c++的上下文中理解它【参考方案6】:

在类方法的情况下使用。详情请查看this reference。

编辑:正如 Adrien 所阐明的,这是一个约定。您实际上可以使用任何东西,但使用 clsself (PEP8)。

【讨论】:

以上是关于Python类中'cls'和'self'之间的区别?的主要内容,如果未能解决你的问题,请参考以下文章

python中静态方法类方法属性方法区别

python Parent.__init()和super(Child, self)的区别

self与cls的区别:python中类方法的定义

Python函数`cls.score`和`clf.cv_results_`之间的区别

python 面向对象(成员,静态,类)的(变量,方法)区别

python单例模式控制成只初始化一次,常规型的python单例模式在新式类和经典类中的区别。