写给小白的Python之018:面向对象-私有成员、@property

导读:

1.私有成员

2.@property

3.访问对象信息

1. 私有成员

在某些情况下,我们希望限制用户访问对象的属性或方法,也就是希望它是私有的,对外隐蔽。

那么,如何在类中定义私有属性或私有方法呢: 在属性名或方法名前加上两个下划线__,使其不能在类的外部使用。

1.类的私有属性 和 私有方法,都不能通过对象直接访问,但是可以在本类内部通过self访问;

2.类的私有属性 和 私有方法,都不会被子类继承,子类也无法访问;

3.私有属性 和 私有方法 往往用来处理类的内部事情,不通过对象处理,避免数据在类的外部被修改,起到安全作用。

4. _x 单前置下划线,私有化属性或方法,在使用from xxx import *时都不会被导入,类对象和子类可以访问,但不要随便访问。_类名__x可以访问。

示例:

class A:
    __str = 'python'
    def __init__(self):
        self.__cook = "fire"

    def __f(self):
        return self.__str

    def f(self):
        return self.__str

a = A()
a.__str # 'A' object has no attribute '__str'
a.__f() # 'A' object has no attribute '__f'
a.f() # 输出: python

修改对象属性值

如果需要修改一个对象的属性值,通常有2种方法:

  • 对象名.属性名 = 数据 ----> 直接修改
  • 对象名.方法名() ----> 间接修改

私有属性不能直接访问,所以无法通过第一种方式修改,一般通过第二种方式修改私有属性的值:定义一个可以调用的公有方法,在这个公有方法内访问修改。

获取和修改私有属性

现代软件开发中,通常会定义get_xxx()方法和set_xxx()方法来获取和修改私有属性值。

# 返回私有属性的值
def get_xxx(self):
    return self.__xxx

# 接收参数,修改私有属性的值
def set_xxx(self, num):
    self.__xxx = num

# 可以通过访问公有方法set_xxx()来修改私有属性的值
对象.set_xxx(100)

# 可以通过访问公有方法get_xxx()来获取私有属性的值
print(对象.get_xxx())

 

2. @property

要调用那些私有属性怎么办?

可以使用property函数。 请看下面的例子:

__metaclass__ = type
class ProtectMe:

    def __init__(self):
        self.me = "xiao"
        self.__name = "kivi"

    @property
    def name(self):
        return self.__name

    @name.setter
    def name(self, value):
        if len(name) > 10:
            print("name的长度太长了")
        self.__name = value


if __name__ == "__main__":
    p = ProtectMe()
    print(p.name)  # kivi
    p.name = "salmond"
    print(p.name)  # salmond

运行结果:
kivi
salmond

从上面可以看出, 用了@property之后, 再调用那个方法的时候, 用p.name的形式,就好像在调用以往非私有化属性一样。

把一个 getter 方法变成属性,只需要加上@property 就可以了,此时,@property 本身又创建了另一个装饰器@score.setter,负责把一个 setter 方法变成属性赋值,于是,我们就拥有一个可控的属性操作。至于装饰器,我们以后再讲。

3. 获取对象信息

type(obj)

使用 type(obj) 来获取对象的相应类型

>>> dog1 = Animal ( ’ dog1 ’ )
>>> type ( dog1 )
__main__. Animal

isinstance(obj, type)

使用 isinstance(obj, type) 判断实例对象是否为指定的 type 类型的实例(类 classname 或其子类的实例)即`object._class `是 class_name 或其子类时返回 True。

>>> isinstance(object, class_name)
True

issubclass(class1, class2)

issubclass(class1, class2) :用于检查类 class1 是不是 class2 的子类。例如 issubclass(bool, int) 会返回 True,因为 bool 是 int 的子类。

hasattr/getattr/setattr

  • 使用 hasattr(obj, attr) 判断对象是否具有指定属性/方法;
  • 使用 getattr(obj, attr[, default]) 获取属性/方法的值, 要是没有对应的属性则返回 default 值(前提是设置了 default),否则会抛出 AttributeError 异常;
  • 使用 setattr(obj, attr, value) 设定该属性/方法的值,类似于 obj.attr=value。

dir(obj)

获取对象所有属性和方法名的列表。

 

posted @ 2018-05-16 07:05  salmond  阅读(383)  评论(1编辑  收藏  举报