Python3 (入门5) 类

来源:互联网 发布:sql删除语句大全 编辑:程序博客网 时间:2024/05/21 12:28

原文:http://blog.csdn.net/rozol/article/details/69317339

定义类

#coding=utf-8# class_my.py 定义类 (新式类)# 定义类class Person:    # 类属性 (class) (注:类/类方法 能修改类属性; 对象不能修改类属性,更改的只是实例属性)    name = "name" # 公共属性    __adress = "adress" # 私有属性 (__属性 表示私有)    # 构造方法(对象创建调用) (__init__ 表示构造)    def __init__(self, name, address = "地球"):        # 实例属性        self.name = name # (注:类属性与实例属性名称相同时用实例属性,实例属性被删除后使用类属性)        self.__adress = address        Person.setData(self)    # 析构方法(对象销毁调用) (__del__ 表示析构)    def __del__(self):        print("对象被销毁.")    # toString()    def __str__(self):        return "Person.class"    # 实例方法 (this)    def setName(self, name): # self可为其他字符串 (this)        self.name = name; # 修改 实例属性 (不存在自动添加)    # 类方法 (static)    @classmethod    def setName_cls(cls, name):        cls.name = name  # 修改 类属性    # 静态方法 (tools)    @staticmethod    def setName_sta(name): # (注:参数部分)        return name    def getName(self):        return self.name    def setData(self):        # 实例属性        self.__age = 21 # 私有属性        self.sex = "女" # 公共属性    def show(self):        print("Hello! %s"%self.name)        print("Address:%s"%self.__adress) # 使用自身私有属性        self.__eat() # 使用自身私有方法    def __eat(self): # 私有方法        print("eat")# ======= 函数调用 ======if __name__ == "__main__":    # - 创建对象 -    ps = Person("LY")    # --- 调用方法 ---    # 调用实例方法    ps.setName("LY") # 实例调用 实例方法    ps.show()    # 调用类方法    Person.setName_cls("Person") # 类调用 类方法    ps.setName_cls("Person") # 实例调用 类方法    # 调用静态方法 ()    print(ps.setName_sta("Per")) # 实例调用 静态方法    print(Person.setName_sta("Per")) # 类调用 静态方法    # --- 访问属性 ---    print(ps.getName())    print(ps.name) # 访问 类属性 的公共属性值    print(ps.sex) # 访问 实例属性 的公共属性值    # --- 修改属性 ---    # 修改实例属性    ps.name = "123" # 修改 类属性 (注:并非真修改,只是向对象中创建了一个实例属性)    del ps.name # 删除 实例属性 (注:实例不能(非类方法)删除 类属性, 只是删除了对象中创建的实例属性,类属性依然存在)    del ps.sex # 删除 实例属性 (注:真删除,删除后不能访问)    # 修改类属性    Person.name = "Person" # 修改类属性    Person.setName_cls("Person") # 类 调用 类方法 修改 类属性 (注:类不能调用实例方法)    ps.setName_cls("Person") # 对象 通过 类方法 修改 类属性    del Person.name # 删除类属性    # - 删除对象 -    del ps    # > Less is more! "静态方法"和"类方法/属性"同级都可理解为"静态",静态方法适合做工具箱,类方法/属性可认为在静态区,随手拿来即用,而实例则需要实例化才能使用. (--本人的个人理解)# ======= 函数调用 ======

继承

#coding=utf-8# class_extend.py 继承(新式类)# --- 单继承 ---# 父类class Animal(object):    def __init__(self, name = "动物"):        self.name = name    def run(self):        print("%s在跑."%self.name)# 子类class Cat(Animal): # 继承 (父类写()内)    def __init__(self, name, ot = ""):        super(Cat, self).__init__(name)    def miao(self):        print("喵")# --- 多继承 ---class Donkey: # 驴    def walk(self):        print("walk")    def eat(self):        print("Donkey.eat")class Horse: # 马    def run(self):        print("run")    def eat(self):        print("Horse.eat")class Mule(Donkey, Horse): # 骡(驴+马)    pass# === 多态 ====def animalRun(animal): # 参数接收自己及其自己的子类    animal.run()# ======= 函数调用 ======if __name__ == "__main__":    # - 单继承调用 -    ani = Animal()    ani.run()    cat = Cat("猫")    cat.run()    cat.miao()    # - 多继承调用 -    mule = Mule()    mule.walk()    mule.run()    mule.eat() # 多个父类中有相同的方法时,调用()内最前面的父类(Donkey)的方法    # - 多态调用 -    ani = Animal()    animalRun(ani)    cat = Cat("猫")    animalRun(cat)# ======= 函数调用 ======

重写

#coding=utf-8# class_rewrite.py 重写(新式类)class Animal(object):    def run(self):        print("Animal.run")    def eat(self, food = "食物"):        print("eat:%s"%food)class Cat(Animal):    # 子类重写了父类的方法    def run(self):        print("Cat.run")    def eat(self):        # 调用父类的方法        super(Cat, self).eat("猫粮")# ======= 函数调用 ======if __name__ == "__main__":    ani = Animal()    ani.run()    ani.eat()    cat = Cat()    cat.run()    cat.eat()# ======= 函数调用 ======

属性方法

#!/usr/bin/env python# coding=utf-8__author__ = 'Luzhuo'__date__ = '2017/5/13'# class_propertiemethod.py 属性方法# 属性方法: 把方法变成静态属性# 写法1class PM_1(object):    def __init__(self):        self.__name_str = "PropertieMethod_1"    # 获取    @property    def name(self):  # 注意,方法名相同        return self.__name_str    # 设置    @name.setter    def name(self, name):        self.__name_str = name    # 删除    @name.deleter    def name(self):        del self.__name_strif __name__ == "__main__":    pm = PM_1()    print(pm.name)    pm.name = "PM"    print(pm.name)    del pm.name    # print(pm.name)# ==========================================================# 写法2class PM_2(object):    def __init__(self):        self.__name_str = "PropertieMethod_2"    # 获取    def getname(self):        return self.__name_str    # 设置    def setname(self, name):        self.__name_str = name    # 删除    def delname(self):        del self.__name_str    # property(fget=None, fset=None, fdel=None, doc=None) # 返回一个property 属性, 实现原理见 内置函数 文章 property_my 块代码(http://blog.csdn.net/rozol/article/details/70603230)    name = property(getname, setname, delname)if __name__ == "__main__":    p = PM_2()    print(p.name)    p.name = "PM2"    print(p.name)    del p.name    # print(p.name)

反射

#!/usr/bin/env python# coding=utf-8__author__ = 'Luzhuo'__date__ = '2017/5/13'# class_reflection.py 反射# 通过反射机制,可动态修改程序运行时的状态/属性/方法# Python的反射机制性能如何? 在Android中Java的反射产生垃圾而执行gc,从而导致UI不流畅,而且性能低# Python的反射性能(1亿次测试): 直接获取属性值:反射获取属性值 = 1:1.164 ;直接设置属性值:反射设置属性值 = 1:1.754def setname(self, name):    self.name = nameclass Clazz(object):    def __init__(self):        self.name = "Clazz"    def getname(self):        return self.nameif __name__ == "__main__":    c = Clazz()    # --- 方法 ---    if hasattr(c, "getname"):        # 获取        method = getattr(c, "getname", None)        if method:            print("setname_ref: {}".format(method()))  # 获取方法对象并执行    if not hasattr(c, "setname"):        # 添加        setattr(c, "setname", setname)  # 添加方法        method = getattr(c, "setname", None)        if method:            method(c, "Reflection")        print("setname_raw: {}".format(c.getname()))    if hasattr(c, "setname"):        # 删除        delattr(c, "setname")        # c.setname(c, "Demo")    # --- 属性 ---    if not hasattr(c, "age"):        # 添加        setattr(c, "age", 21)  # 添加方法        var = getattr(c, "age", None)        print("age_ref: {}".format(var))        print("age_raw: {}".format(c.age))    if hasattr(c, "age"):        # 获取        var = getattr(c, "age", None)        print("age_ref: {}".format(var))    if hasattr(c, "age"):        # 删除        delattr(c, "age")        # print("age_raw: {}".format(c.age))

文档注释

#!/usr/bin/env python# coding=utf-8__author__ = 'Luzhuo'__date__ = '2017/5/13'# class_doc.py 文档注释# 文档注释的编写class Foo(object):    '''    这是一个类    '''    def method(self, data):        '''        这是一个方法        :param data: 需要的数据        :return: 返回的数据        '''        return "method"def func(data):    '''    这是一个函数    :param data: 需要的数据    :return: 返回的数据    '''    return "func"if __name__ == "__main__":    # 打印文档    print(Foo.__doc__)    print(Foo().method.__doc__)    print(func.__doc__)

创建类的原理

#!/usr/bin/env python# coding=utf-8__author__ = 'Luzhuo'__date__ = '2017/5/13'# class_origin.py 类的由来# 类由type类实例化产生, 而type由解释器产生age = 21def __init__(self):    self.name = "origin"def getname(self):    return self.namedef setname(self, name):    self.name = namedef delname(self):    del self.nameif __name__ == "__main__":    # 用type创建类(类名, 基类元组, 类成员字典)    Foo = type('Foo', (object,), {'__init__' : __init__, "getname" : getname, "setname" : setname,                                  "delname": delname, "age" : age})    # 实例化类    f = Foo()    # 使用    print(f.age)    print(f.getname())    f.setname("ClassOrigin")    print(f.getname())    f.delname()    # print(f.getname())# ==================================================================================# 元类 (type创建类原理)# 元类是用于创建所有类的类, Python中是type类 (注意,类也是对象,也是被创建出来的,即万物皆对象), 下面将演示type类的功能# __call__ 的调用 (__new__在__init__之前调用, __call__在什么时候调用呢)class Foobar(object):    def __call__(self, *args, **kwargs):        print("Foobar __call__")if __name__ == "__main__":    fb = Foobar()    fb()  # 只有在这个时候才会调用__call__属性    Foobar()()  # 等同于该方式# ------# metaclass指定类有谁来创建# Python创建类时会寻找__metaclass__属性,(包括父类)没有找到将使用内建元类typeclass MyType(type):    def __init__(self, *args, **kwargs):        print("MyType __init__")    def __call__(self, *args, **kwargs):        print("MyType __call__")        obj = self.__new__(self)        self.__init__(obj, *args, **kwargs)        return obj    def __new__(cls, *args, **kwargs):        print("MyType __new__")        return type.__new__(cls, *args, **kwargs)class Foo(object, metaclass=MyType):  # (Python3.x写法) metaclass 用于创建类, Python创建类时会寻找__metaclass__属性,(包括父类)没有找到将使用内建元类type    # __metaclass__ = MyType # Python2.x写法    def __init__(self):        print("Foo __init__")    def __new__(cls, *args, **kwargs):  # 用于实例化对象        print("Foo __new__")        return object.__new__(cls)  # 必须是返回    def show(self):        print("Foo show")if __name__ == "__main__":    print("start")    f = Foo()    f.show()    # MyType __new__ => MyType __init__ => 'start' => MyType __call__ => Foo __new__ => Foo __init__ => 'Foo show'

其他的一些补充

#!/usr/bin/env python# coding=utf-8__author__ = 'Luzhuo'__date__ = '2017/5/13'# class_other.py 关于类的一些补充class Demo(object):    def show(self):        print("Demo show")if __name__ == "__main__":    # __module__ 该对象的模块名    # __class__ 该对象的类对象    print(Demo.__module__)  # 该对象的模块名 => __main__    print(Demo.__class__)  # 该对象的类对象 => <class 'type'>    obj = Demo()    print(obj.__module__)  # 该对象的模块名 => __main__    print(obj.__class__)  # 该对象的类对象 => <class '__main__.Demo'>    obj.__class__.show(obj)  # 类对象可被使用    # ============================    # __dict__ 类或对象中的所有成员    print(Demo.__dict__)  # 类属性    print(obj.__dict__)  # 实例属性
原创粉丝点击