在 python 中定义私有模块函数

新手上路,请多包涵

根据 http://www.faqs.org/docs/diveintopython/fileinfo_private.html

像大多数语言一样,Python 有私有元素的概念:

  • 私有函数,不能 从其模块外部 调用

但是,如果我定义两个文件:

 #a.py
__num=1

和:

 #b.py
import a
print a.__num

当我运行 b.py 它打印出 1 没有给出任何异常。是diveintopython错了,还是我误解了什么?有没有 办法 将模块的功能定义为私有的?

原文由 olamundo 发布,翻译遵循 CC BY-SA 4.0 许可协议

阅读 822
2 个回答

在 Python 中,“隐私”取决于“同意成年人”的协议水平——你不能 强迫 它(就像你在现实生活中一样;-)。一个前导下划线意味着您不 应该“从外部”访问它 - 两个 前导下划线(没有尾随下划线)更加有力地传达信息……但最终,它仍然取决于社交约定和共识:Python 的自省功能足够强大,以至于你不能给世界上所有其他程序员 戴上手铐 来尊重你的意愿。

((顺便说一句,虽然这是一个保密的秘密,但对于 C++ 来说也是如此:对于大多数编译器,在 — 之前有一个简单的 #define private public#include .h 文件狡猾的编码人员只需要对您的“隐私”进行散列…!-))

原文由 Alex Martelli 发布,翻译遵循 CC BY-SA 3.0 许可协议

class privatesmodule privates 之间可能存在混淆。

私有模块一个下划线开头

使用导入命令的 from <module_name> import * 形式时不会复制这样的元素;但是,如果使用 import <moudule_name> 语法,它会被导入( 参见 Ben Wilhelm 的回答

只需从问题示例的 a.__num 中删除一个下划线,它就不会显示在使用 from a import * 语法导入 a.py 的模块中。

私有类两个下划线开头(又名双下划线,即 d-double 下划线)

这样的变量的名称被“损坏”以包含类名等。

它仍然可以通过错位名称在类逻辑之外访问。

尽管名称重整可以作为防止未授权访问的温和预防措施,但其主要目的是防止可能与祖先类的类成员发生名称冲突。请参阅 Alex Martelli 在描述关于这些变量的约定时对 同意的成年人 的有趣但准确的参考。

 >>> class Foo(object):
...    __bar = 99
...    def PrintBar(self):
...        print(self.__bar)
...
>>> myFoo = Foo()
>>> myFoo.__bar  #direct attempt no go
Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
AttributeError: 'Foo' object has no attribute '__bar'
>>> myFoo.PrintBar()  # the class itself of course can access it
99
>>> dir(Foo)    # yet can see it
['PrintBar', '_Foo__bar', '__class__', '__delattr__', '__dict__', '__doc__', '__
format__', '__getattribute__', '__hash__', '__init__', '__module__', '__new__',
'__reduce__', '__reduce_ex__', '__repr__', '__setattr__', '__sizeof__', '__str__
', '__subclasshook__', '__weakref__']
>>> myFoo._Foo__bar  #and get to it by its mangled name !  (but I shouldn't!!!)
99
>>>

原文由 mjv 发布,翻译遵循 CC BY-SA 3.0 许可协议

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