Python 类属性 下划线的意义是什么?

我发现 _A 是可以访问的但是 __B 是无法访问的会报错:Unexpect System Error:'A' object has no attribute ....

class A:

    @property
    def _A(self):

    @property
    def __B(self):
 

不是说下划线只是约定而已么,怎么其实还是有实际作用的

阅读 1k
avatarAI BotBETA

在Python中,以单下划线_A开头的类属性被视为是保护属性,即该属性不应该被直接访问,而应该通过类的其他方法进行访问。因此,你可以在类内部访问_A属性,但不能从类的外部直接访问。

另一方面,以双下划线__B开头的类属性被视为是私有的类属性。这意味着该属性只能在类内部访问,无论是通过实例还是类本身。尝试从类的外部直接访问__B属性将会引发错误。

这两种约定是用于提供一定的代码可读性和保护。使用下划线前缀可以明确表明属性的访问级别,从而帮助其他开发人员更好地理解代码并避免意外的错误。

在你的代码示例中,__B属性是私有的,因此无法从类的外部直接访问。如果你尝试这样做,将会收到类似于'A' object has no attribute '__B'的错误消息。

总结起来,单下划线_A表示保护属性,可以在类内部访问但不应直接从外部访问;双下划线__B表示私有属性,只能在类内部访问。这些约定是用于提高代码的可读性和保护性。

2 个回答

双下划线比单下划线多了 Name Mangling,这是个 Python 2.0 时引入的新特性。你可以直接理解成编译器会把属性名替换成别的。

但如果你知道编译器是怎样替换的(一般来说是 _类__属性,具体到题目中的例子就是 _A__B),你照样可以在外部访问到它。换而言之,它依然还是“公有”的,只是被编译器改了名字。

因此我们说 Python 并没有真正的属性可见性修饰符,下划线仅仅是约定俗成。

private variables

“Private” instance variables that cannot be accessed except from inside an object don’t exist in Python. However, there is a convention that is followed by most Python code: a name prefixed with an underscore (e.g. _spam) should be treated as a non-public part of the API (whether it is a function, a method or a data member). It should be considered an implementation detail and subject to change without notice.

Since there is a valid use-case for class-private members (namely to avoid name clashes of names with names defined by subclasses), there is limited support for such a mechanism, called name mangling. Any identifier of the form __spam (at least two leading underscores, at most one trailing underscore) is textually replaced with _classname__spam, where classname is the current class name with leading underscore(s) stripped. This mangling is done without regard to the syntactic position of the identifier, as long as it occurs within the definition of a class.

双下划线确实有“实际作用”。它会触发 name mangling ,实际存在的成员名字会被增加一个修饰。它在类外无法直接被使用,从而是“私有的”。


在类外使用修饰后的名字是可以访问的。

撰写回答
你尚未登录,登录后可以
  • 和开发者交流问题的细节
  • 关注并接收问题和回答的更新提醒
  • 参与内容的编辑和改进,让解决方法与时俱进
推荐问题
宣传栏