Python中双前导下划线__var的正确理解

近期作者发现很多Python学习者居然把双前导下划线(也就是双下划线前缀)理解成私有属性了,甚至是很多Python教程中也这么理解,这让作者感到惊讶。

首先先看一段代码:

class test:
    def __init__(self,name):
        self.__name = name
 
A = test('张飞')
print(A.__name)

可以发现,对象A通过对__name属性的访问,直接造成了AttributeError。

这样看起来似乎self.__name是被私有化了,然而事实真是这样么?

双前导下划线的作用

双前导下划线会导致Python解释器重写属性名,以避免子类中的命名冲突,这也叫做名称修饰。解释器更改变量的名称,以便在类被扩展的时候不容易产生冲突。

通俗的讲,使用双前导下划线的变量,会被编译器重新命名,并非是变量私有化。

那变量被改成什么了呢?

print(dir(A))

打印出对象A的所有属性和方法,并没有找到__name,却找到了一个_test__name的属性;

没错,_test__name就是被更名后的变量,单下划线+类名+变量名。

print(A._test__name)

这样就可获得所谓的“私有属性”了。

再来看一段代码:

_test__name = '张飞'
 
class test:
    def getName(self):
        return __name
 
A = test()
print(A.getName())

你猜会发生生么?

原创内容,如需转载,请注明出处;

本文地址: https://www.perfcode.com/p/970.html

分类: 计算机技术
推荐阅读:
如何查看CPU序列号 请注意,某些CPU可能没有序列号,或由于制造商实施的安全功能而无法获取序列号。此外,序列号可能不是针对您特定的CPU型号而独有的,可能在多个CPU之间共享。
Python max()函数 max() 是 Python 中的一个内置函数,用于返回给定可迭代对象中的最大值。
Rust stringify宏的用法和示例 在Rust中,stringify是一个宏,它接受任何合法的Rust标识符,并将其转换为字符串;这种转换发生在编译时,而不是运行时,这意味着它对于生成代码或诊断消息非常有用。
解决rust-analyzer在rustlings中不生效的问题 rustlings是一个让你习惯阅读和编写Rust代码的项目,其中包含一些小练习;当使用VSCode打开该项目并编写练习时,rust-analyzer插件可能没有生效;
PySide6 事件的传播机制 在PySide6中,界面上的按钮(QPushButton)和QWidget部件都可以定义keyPressEvent来处理键盘按键事件。当按键事件发生时,系统会根据事件的传播机制来确定哪个部件的keyPressEvent方法将被执行。
Rust:formatting specifier missing 错误解决方法 编译Rust程序时,出现 formatting specifier missing 错误,导致该错误的原因可能是错误的使用println!宏;