【python】Python变量/方法中 _xx、__xx的区别

Python中不存在真正意义上的私有方法,为了实现类似于c++中私有方法,可以在类的方法或属性前加一个“_”单下划线,或者“__"双下划线

"_xx"单下划线

意味着该方法或属性外部不应该去调用,它并不属于API。但这只是一种约定,其实这样的实例变量外部是可以访问的。即它是表面私有。

  • 可被外部访问(但不建议)
  • 可被子类继承(但不建议)

"__xx"双下划线

  • 不可被外部访问
  • 不可被继承
    只有在类内部进行访问,所以外部访问时可在类中自定义方法实现, 由于它不可被子类继承,可以避免被子类覆盖。

"__xx"的形式

  • 类属性
class Student:
    __name = "zhangsan"
  • 实例属性
class Student:
    def __init__(self):
        self.__name = "zhangsan"

外部访问"__xx"的几种方式

  • 方式一(建议永远不要用)
class Student:
    __name = "zhangsan"

s = Student()
s._Student__name
# 'zhangsan'
  • 方式二

在类的内部自定义get_age()和set_age()两个函数供外界调用私有化属性

class Student:
    def __init__(self):
        self.__age = 18 #定义一个私有化属性
        pass
    def get_age(self):
        return self.__age
    def set_age(self,age):
        if age<0:
            print('age can not under 0')
            pass
        else:
            self.__age = age
            pass
        pass

s = Student()
s.get_age()
# 18
  • 方式三

property

class Student:
    def __init__(self):
        self.__name = "zhangsan"

    def get_name(self):
        return self.__name

    def set_name(self, value):
        self.__name = value

    def del_name(self):
        del self.__name

    name = property(get_name, set_name, del_name, "I'm the 'x' property.")

s= Student()
s.name
Out[4]: 'zhangsan'

s.name = "lisi"
s.name
Out[6]: 'lisi'

del s.name
s.name
Traceback (most recent call last):
  File "C:\Users\ISSUSER\AppData\Local\Programs\Python\Python37\lib\site-packages\IPython\core\interactiveshell.py", line 3444, in run_code
    exec(code_obj, self.user_global_ns, self.user_ns)
  File "<ipython-input-8-98b019fbfe94>", line 1, in <module>
    s.name
  File "<ipython-input-2-7f819d4fa85e>", line 6, in get_name
    return self.__name

  • 方式四

property装饰器

class Student:
    def __init__(self):
        self.__name = "zhangsan"
    @property
    def name(self):
        """I'm the 'name' property."""
        return self.__name

   # 注意这些额外函数的名字和property下的一样,例如这里的name
   # 分别被name.setter, name_deleter装饰
    @name.setter
    def name(self, value):
        self.__name = value
    @name.deleter
    def name(self):
        del self.__name

s = Student()
s.name
Out[11]: 'zhangsan'
s.name = "wangwu"
s.name
Out[13]: 'wangwu'

posted @ 2022-07-26 15:20  倒骑驴子  阅读(415)  评论(0)    收藏  举报