面向?qū)ο笾R點(diǎn)總結(jié)

目錄
import time

def init_str_del():
    class Teacher(object):
        # 類屬性:在方法外、類內(nèi)部定義的屬性
        # 對象沒創(chuàng)建的時(shí)候就想使用一個(gè)屬性 那么就可以定義一個(gè)類屬性
        country = "中國"

        # 隱匿的添加對象屬性
        # 實(shí)例屬性:在init方法內(nèi)定義的屬性
        def __init__(self,name,age):
            self.name = name
            self.age = age

        # 輸出對象的時(shí)候,不想看到對象的內(nèi)存地址,那么魔法方法__str__可以返回對象的描述信息
        def __str__(self):
            # 返回一個(gè)字符串信息
            return '我叫:%s 年齡:%d' % (self.name, self.age)

        # 1.程序退出,程序中所使用到的對象全部銷毀
        # 2.當(dāng)前對象的內(nèi)存地址沒有變量使用的時(shí)候,那么對象銷毀
        def __del__(self):
            print('對象被釋放了:', self)

        def show_info(self):
            print("python3里的舊式類自動繼承object")
            print(self.name, self.age)

    teacher = Teacher('鄧川', 21)
    teacher.show_info()

    '''################### 類屬性的操作 ###################'''
    # 訪問類屬性
    print(Teacher.country)
    # 使用類不能訪問對象屬性
    # print(Teacher.age)

    # 修改類屬性
    Teacher.country = '中國0'
    print(Teacher.country)
    # 查看類屬性和方法
    print(Teacher.__dict__)

    '''################### 實(shí)例屬性的操作 ###################'''
    print(teacher.name)
    # 對象可以訪問類屬性
    print(teacher.country)

    # 對象不能修改類屬性,其實(shí)是添加了一個(gè)對象屬性
    print("-" * 20)
    print(Teacher.__dict__)
    print(teacher.__dict__)
    teacher.country = '中國人1'
    print(teacher.country)
    print(Teacher.__dict__)
    print(teacher.__dict__)

    # 其實(shí)記住一個(gè)原則就好,類屬性由類去操作,實(shí)例屬性由對象去操作就不會出錯!??!
    # 對象可以訪問類屬性 不能修改

    print(teacher.__dict__)
    # 使用實(shí)例修改對象屬性
    teacher.name = '李四'
    print(teacher.name)
    print(teacher.__dict__)

    '''################### 靜態(tài)動態(tài)添加屬性 ###################'''

    # 沒有init方法的時(shí)候,可以動態(tài)的添加對象屬性
    teacher.name = '李四'
    teacher.age = 18
    teacher.show_info()
    # 可以修改屬性
    teacher.name = '王五'
    print(teacher.name, teacher.age)

    # 查看Teacher類繼承的父類
    print(Teacher.__bases__)

    '''################### __str__方法 ###################'''

    # 輸出對象 自動調(diào)用__str__方法
    print(teacher)

    '''################### __del__方法 ###################'''
    # 刪除變量     => 對象先釋放再退出 (第2種)
    del teacher
    # => 程序退出了對象再被釋放(第1種)
    # teacher0 = teacher
    # del teacher

    # 引用計(jì)數(shù):內(nèi)存地址被變量使用的次數(shù),當(dāng)引用計(jì)數(shù)為0 表示對象被銷毀
    time.sleep(3)
    print('程序退出了')


def single_inherit():
    class Animal(object):
        # 對象方法
        def run(self):
            print("動物跑起來了")

    class Dog(Animal):
        # 重寫:子類繼承父類,父類的方法滿足不了子類的需要可以對父類的方法進(jìn)行重寫
        # 重寫的特點(diǎn):1.繼承關(guān)系 2.方法名相同
        def run(self):
            print("小狗跑起來了")

        def wang(self):
            # 在此調(diào)用父類的方法
            # <1>self,前提:當(dāng)前類里面沒有父類的方法,否則調(diào)用的是當(dāng)前類里面的方法,因?yàn)橹貙懥?            self.run()
            # <2>使用父類的類名 如果使用類名調(diào)用對象方法需要傳入實(shí)例對象
            Animal.run(self)

            # <3>super調(diào)用父類的方法
            # 根據(jù)指定類,在類繼承鏈中獲取下一個(gè)類
            # 提示:1.Dog表示根據(jù)指定類找類繼承鏈中獲取下一個(gè)類
            #      2.self表示獲取self對象類型的類繼承鏈
            #      3.super不一定是你直接繼承的父類?。?!單繼承直接理解成是繼承的父類沒有問題,但是多繼承就有可能不是
            #      4.super調(diào)用的是父類的方法,但是不一定是你直接繼承父類的方法
            super(Dog, self).run()
            print(self.__class__.mro())
            

            print('汪')

    # 在python里面的方法調(diào)用會遵循mro,類繼承順序,也就是在某個(gè)類里找到了就不會再找了
    # print(Dog.mro())
    dog = Dog()

    dog.wang()
    dog.run()


def more_inherit():
    class A(object):
        def show_a(self):
            print('我是A類')

    class B(object):
        def show_b(self):
            print('我是B類')

    class C(A,B):
        def show(self):
            # 查看類的繼承順序
            print(self.__class__.mro())
            # 指定類A要在self對象類繼承順序中找下一個(gè)類
            super(A,self).show_b()
            print('我是C類')
            # super(C,self).show_b()也是可以的?。?!因?yàn)橛欣^承關(guān)系!輸出結(jié)果是一樣的
    C().show()


def init_inherit():
    class A():
        def __init__(self,name):
            print("A")
            self.name = name


    class B(A):
        # 提示:如果子類提供了調(diào)用的方法,那么不會主動調(diào)用父類的方法
        def __init__(self, subject):
            # 調(diào)用父類的__init__方法
            # self.__init__('DC') 這種寫法錯誤 因?yàn)榉椒粯?在這會遞歸

            # 使用類名調(diào)用父類的init方法
            A.__init__(self, '李四')

            # super調(diào)用父類里面的init
            super(B,self).__init__('王五')

            # 簡寫 super() -> super(B,self)
            super().__init__('小明')


            print("B")
            self.subject = subject

        def show(self):
            print("我是B類")

    b = B("PYTHON")
    print(b.subject)
    print(b.name)
    b.show()


def rewrite_super():
    class Person(object):
        def show(self):
            print('我是人類')

    class Plane(object):
        def show(self):
            print('飛機(jī)')

        def fly(self):
            print('飛機(jī)可以飛')

    class Student(Person,Plane):
        def show(self):
            print(self.__class__.mro())
            # 方法重寫也可以使用super,調(diào)用父類的方法
            super(Person,self).show()

    dc = Student()
    dc.show()


def private_attributes_method():
    # 在屬性名和方法名加上 兩個(gè)下劃線 '__' 那么定義的屬性和方法就是私有屬性和私有方法
    class Person(object):
        def __init__(self,name,age):
            self.name = name
            # 私有屬性,只能在本類內(nèi)部使用,在類外面不能使用
            # 注意點(diǎn):私有屬性只能在init方法里面添加
            self.__age = age
            
        def show(self):
            # 在類內(nèi)部使用私有屬性和私有方法是可以的
            print(self.name, self.__age)
            self.__money()

        def __money(self):
            print("100萬")

    person = Person('DC', 20)
    print(person.name)
    # 私有屬性在外界訪問不了
    # print(person.__age)
    person.show()
    # 私有方法在外界訪問不了
    # person.__money()

    # 查看對象中的屬性信息
    print(person.__dict__)
    # 本意是修改私有屬性
    # 在這里不是修改了私有屬性,而是給對象添加了一個(gè)__age的對象屬性
    # 提示:這里也不是添加的私有屬性,只能在init方法里面添加
    person.__age = 22
    print(person.__age)
    print(person.__dict__)
    # 查看類屬性和方法
    print(Person.__dict__)

    # 在python里面私有屬性和私有方法沒有做到絕對的私有,只是進(jìn)行了一個(gè)名字的偽裝
    # 非常規(guī)操作 不建議這樣使用
    print(person.__dict__)
    print(person._Person__age)
    person._Person__age = 34
    print(person.__dict__)
    print(person._Person__age)

    person._Person__money()
    person.show()


def inherit_private():
    class Person(object):
        def __init__(self):
            self.__age = 18

    def __show(self):
        print('我是一個(gè)私有方法')

    class Student(Person):
        # def show(self):
        #     print(student.__age)
        #     student.__show()
        pass

    student = Student()
    # print(student.__age)
    # student.__show()
    # student.show()
    # 總結(jié):子類繼承父類,不能直接使用父類的私有屬性和私有方法


def classMethod_staticMethod():
    class Person(object):
        # 私有類屬性
        __mytype = '黃種人'

    def __init__(self):
        self.name = 'zww'
    # 定義對象方法:在方法的參數(shù)里面有self表示對象方法
    def show(self):
        print('我是人類')

    # 定義類方法 cls表示當(dāng)前類
    @classmethod
    def show_info(cls):
        print(cls)
        print('我是一個(gè)類方法')

    # 定義靜態(tài)方法 提示:靜態(tài)方法和當(dāng)前對象和當(dāng)前類沒有關(guān)系,不會使用self和cls
    @staticmethod
    def show_msg():
        print('我是一個(gè)靜態(tài)方法')

    # 應(yīng)用場景:用類方法可以修改類屬性
    @classmethod
    def set_type(cls, mytype):
        cls.__mytype = mytype

    # 返回一個(gè)類的私有屬性
    @classmethod
    def get_type(cls):
        return cls.__mytype

    # ----------------------------------對象方法是最通用的方法,可以修改對象屬性和類屬性
    def instance_set_type(self, mytype,name):
        # self.__mytype = mytype 不要這樣寫,這樣寫就添加了一個(gè)對象屬性
        # self.__class__ 獲取對象所對應(yīng)的類
        self.__class__.__mytype = mytype

        print(self.name)
        # 修改對象屬性
        self.name = name

    # 獲取對應(yīng)的類屬性
    def instance_get_type(self):
        print(self.name)
        return self.__class__.__mytype

    # ---------------------------------------------------既不需要當(dāng)前對象也不需要當(dāng)前類
    @staticmethod
    def sum_num(num1, num2):
        return num1 + num2

    p = Person()
    p.show()
    p.show_info()
    p.show_msg()

    p.set_type('白種人')
    result = p.get_type()
    print(result)

    p.instance_set_type('黑種人','DC')
    print(p.instance_get_type())
        
    print(p.sum_num(1, 2))

    # 類調(diào)用靜態(tài)方法和類方法不需要傳入當(dāng)前類,如果類調(diào)用對象方法需要傳入一個(gè)實(shí)例
    Person.show_msg()
    # Person.show(p) # 一般都不這樣干
    Person.show_info()  


def polymorphism():
    # 多態(tài): 關(guān)注的是同一個(gè)方法,但是會出現(xiàn)不同的表現(xiàn)形式,在python里不需要關(guān)注類型
    class Text(object):
        def show(self):
            print('顯示文字')

    class Image(object):
        def show(self):
            print('顯示圖片')

    class Video(object):
        def show(self):
            print('顯示視頻')

    class Person(object):
        def show(self):
            print('我在跳舞')

    # 實(shí)現(xiàn)顯示數(shù)據(jù)的功能
    def show_data(data):
        # 關(guān)心的是 同一個(gè) 方法,會出現(xiàn)不同的表現(xiàn)形式,那么這種操作叫做多態(tài)
        # 在python里面多態(tài):只關(guān)心對象的方法,不關(guān)心對象的類型
        data.show()

    image = Image()
    video = Video()
    p = Person()
    show_data(p)


def new():
    # 單例:在應(yīng)用程序中不管創(chuàng)建多少次對象只有一個(gè)實(shí)例對象 內(nèi)存地址是一樣的
    class Person(object):
        
        # 私有的類屬性
        __instance = None

        # 創(chuàng)建對象
        def __new__(cls, *args, **kwargs):
            # if cls.__instance == None:
            if not cls.__instance:
                print("創(chuàng)建對象")
                # 把創(chuàng)建的對象給類屬性
                cls.__instance = object.__new__(cls)
            
            return cls.__instance
        
        def __init__(self,name,age):
            print('初始化')
            self.name = name
            self.age = age

    p1 = Person('張三', 20)
    # p1對象已經(jīng)創(chuàng)建了,在這里返回已經(jīng)創(chuàng)建的對象的內(nèi)存地址,然后對P2對象進(jìn)行初始化
    # p1、p2的內(nèi)存地址是一樣的 p2初始化的內(nèi)容覆蓋了p1初始化的內(nèi)容
    p2 = Person('李四', 22)
    print(p1, p2)
    print(p1.name, p2.name)  # 李四 李四


def slots():
    # 指明創(chuàng)建對象的時(shí)候不能再添加其它屬性,只能是指定的屬性
    class Student(object):
        # 這樣的操作可以讓對象的屬性固定
        __slots__ = ('name', 'age')

        def __init__(self,name,age):
            self.name = name
            self.age = age

    stu = Student('xx', 20)
    print(stu.name,stu.age)

    stu.name = '李四'
    stu.age = 21
    # stu.sex = '女'

    print(stu.name,stu.age)


def method_to_variable():
    '''
    class Student(object):
        
        def __init__(self):
            self.__score = 100

        def set_score(self, score):
            self.__score = score

        def get_score(self):
            return self.__score

    stu = Student()
    score = stu.get_score()
    print(score)

    stu.set_score(99)
    score = stu.get_score()
    print(score)
    '''
    class Student(object):
        
        def __init__(self):
            self.__score = 100
            
        # 把方法改成對應(yīng)的屬性
        # 獲取值
        @property
        def get_score(self):
            return self.__score

        # 設(shè)置值
        @get_score.setter
        def set_score(self, score):
            self.__score = score

    stu = Student()
    score = stu.get_score
    print(score)

    stu.set_score = 80
    score = stu.get_score
    print(score)



if __name__ == '__main__':
    # variable靜態(tài)動態(tài)的添加 魔法方法str和del
    init_str_del()

    # 單繼承 使用類名調(diào)用父類的方法
    single_inherit()
    
    # 多繼承 super的使用
    more_inherit()

    # __init__方法中使用super
    init_inherit()

    # 在重寫方法中使用super
    rewrite_super()

    # 私有屬性和私有方法
    private_attributes_method()

    # 子類不能直接使用父類的私有屬性和私有方法
    inherit_private()

    # 類方法和靜態(tài)方法
    classMethod_staticMethod()

    # 多態(tài)
    polymorphism()

    # 單例
    new()

    # 指明創(chuàng)建對象的時(shí)候不能再添加其它屬性,只能是指定的屬性
    slots()

    # 把方法改成對應(yīng)的屬性
    method_to_variable()
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請聯(lián)系作者
【社區(qū)內(nèi)容提示】社區(qū)部分內(nèi)容疑似由AI輔助生成,瀏覽時(shí)請結(jié)合常識與多方信息審慎甄別。
平臺聲明:文章內(nèi)容(如有圖片或視頻亦包括在內(nèi))由作者上傳并發(fā)布,文章內(nèi)容僅代表作者本人觀點(diǎn),簡書系信息發(fā)布平臺,僅提供信息存儲服務(wù)。

相關(guān)閱讀更多精彩內(nèi)容

友情鏈接更多精彩內(nèi)容