Python本地变量与self的区别

4
在下面的代码中,self.x+self.yx+y有什么区别?
class m2:
    x, y = 4, 5
    def add(self, x, y):
        return self.x + self.y
    def add2(self, x, y):
        return x + y

>>> x = m2()
>>> print "x.add(self.x + self.y = )", x.add(1, 2)
x.add(self.x + self.y = ) 9
>>> print "x.add2(x + y = )", x.add2(1, 2)
x.add2(x + y = ) 3

为什么 self.x + self.y 返回值是 9,而 x + y 的返回值是 3

可能是Python:类属性和实例属性的区别的重复问题。 - idjaw
2
@idjaw 我认为这不是你链接的那个问题的重复。这个问题中没有单个实例属性,因此它与混淆类和实例属性无关。 - Sven Marnach
6
首先,add 方法会将 self 对象的属性值相加。而在第二个方法 add2 中,则是对传递进来的参数值进行相加。 - Dan D.
@SvenMarnach 我太急了,谢谢你提醒我。撤回。 - idjaw
5个回答

3

add中,你调用了类变量并忽略了方法参数xy

class m2:

    # these variables are class variables and are accessed via self.x and self.y
    x, y = 4, 5  

    def add(self, x, y):
        return self.x + self.y  # refers to 4 and 5

    def add2(self, x, y):
        return x + y  # refers to input arguments x and y, in your case 1 and 2

当在类作用域中定义xy时,它们成为类变量。它们是类m2的一部分,您甚至不需要创建m2的实例来访问它们。

print m2.x, m2.y
>> 4, 5

然而,您也可以通过实例访问它们,就像访问实例变量一样,如下所示:
m = m2()
print m.x, m.y
>> 4, 5

这是因为解释器会寻找名为self.xself.y的实例变量,如果没有找到,则会默认使用类变量。
在Python的文档中了解更多关于类属性的内容。

1
当调用类方法时,第一个参数(按惯例命名为self)被设置为类实例。当该方法访问self的属性时,它正在访问该类实例中的这些属性,并且它们的值在该实例中持久存在。
另一方面,如果类方法访问裸变量,则这些变量严格局限于这些方法,并且它们的值不会跨类方法调用持久存在于该实例中。

1
区别在于当你使用self时,你是在引用类实例的成员变量
当你直接使用X和Y时,你是在引用函数中使用的参数
这是对你的类的简化。
class m2:
    x_member1, y_member2 = 4, 5
    def add(self, x_parameter1, y_parameter2 ):
            return self.x_member1+ self.y_member2
    def add2(self, x_parameter1, y_parameter2 ):
            return x_parameter1 + y_parameter2

1
class m2:
    x, y = 4, 5 #This are class attributes
    def add(self, x, y ):
            return self.x + self.y # This are instance variables
    def add2(self, x, y ):
            return x + y # This are local variables

类变量对于该类的每个实例都是共同的。实例变量仅适用于该实例。局部变量仅在函数范围内可用。

add中,当您执行self.x时,它引用了类变量x,因为它也是实例的一部分。在add2中,它引用局部变量。

如果这些方法是类方法或静态方法(进行适当的调整),则可以实现相同的结果。

类方法:

class m2:

    x, y = 4, 5

    @classmethod
    def add(cls, x, y):
        return cls.c + cls.y #Here you're calling class attributes

    @classmethod
    def add2(cls, x, y):
        return x + y

结果:

>>> m.add(1,2)
9
>>> m.add2(1,2)
3

静态方法:
class m2:
    x, y = 4, 5

    @staticmethod
    def add(x, y):
        return m2.c + m2.y #Here you need to call the class attributes through the class name

    @staticmethod
    def add2(x, y):
        return x + y

结果:

 >>> m2.add(1,2)
 9
 >>> m2.add2(1,2)
 3

0

x和y默认情况下将是本地变量。self.x和self.y在该实例中持久存在,x和y仅在本地存在。

class Dog():
    def __init__(self):
        x = "local"
        self.y = "instance"

d = Dog()
print(d.y)
#=> instance
print(d.x)
#=> AttributeError: Dog instance has no attribute 'y'

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接