python(13)面向對象、方法

一、面向對象

程序       現實

對象——————>具體的事物

 

現實的事物——————>轉成電腦程序

世間萬物皆對象

 

優點:

提高代碼複用性

 

面向對象:

類、對象、屬性、方法

 

對象的集合

------>  類別

------>  共同的特徵  屬性

------>  動作  方法

多個對象 ————> 提取對象共同的特徵和動作 ————> 封裝到一個類中

#所有類名,要求首字母大寫,多個單詞使用駝峯式命名
'''
繼承
class 類名[(父類)]:
    屬性  特徵
    方法  動作
'''
class Phone:
    #屬性
    brand = 'huawei'
    #方法

#使用類 創建對象
p = Phone()
print(p)

print(p.brand)
#定義類和屬性
class Student:
    #類屬性
    name = 'aaa'
    age = '2'

#先找自己空間的,再去模型中找,如果自己空間中存在age屬性,不會去模型類中查找
#使用類,創建對象
tom = Student()
#對象屬性  動態創建屬性,屬於自己
tom.name = 'tom'
tom.age = 18
print(tom.name)

lucy = Student()
lucy.name = 'lucy'
lucy.age = 30
print(lucy.name)

#修改Student類中的屬性值
Student.name = 'bbb'

 

二、方法

類中方法:動作

種類:  普通方法  類方法  靜態方法  魔術方法

普通方法格式:

def 方法名(self[,參數, 參數])

 

類方法:  裝飾器@classmethod    調用方法:類名.類方法()

不依賴於對象,可以獨立對象

特點:

1、定義需要依賴裝飾器@classmethod

2、類方法中的參數不是一個對象,而是當前類

3、類方法中只可以使用類屬性

4、類方法中不能使用普通方法,方法中有self,方法依賴self,而類方法無法傳遞self參數

格式:

@classmethod

def 方法名(cls):

    pass

 

類方法的作用:

因爲只能訪問類屬性和類方法,所以可以在對象創建之前,如果需要完成一些動作(功能)


 

靜態方法:  類似於類方法

1、需要裝飾器@staticmethod

2、靜態方法是無需傳遞參數cls或self

3、也只能訪問類的屬性和方法,無法訪問對象的屬性和方法

4、加載時機同類方法

 

格式:

@staticmethod

def 方法名():

    pass

 

總結:類方法 和 靜態方法

不同:

1、裝飾器不同歐冠

2、類方法是有參數的,靜態方法沒有參數

 

相同:

1、只能訪問類的屬性和方法,對象的屬性和方法無法訪問

2、都可以通過類名調用訪問

3、都可以在創建對象之前使用,因爲是不依賴於對象的

 

普通方法 與 類方法和靜態方法的區別:

不同:

1、沒有裝飾器

2、普通方法永遠是要依賴對象,因爲每個普通方法都有一個self  self爲對象本身

3、只有創建了對象纔可以調用普通方法,否則無法調用

 

魔術方法:

__init__: 初始化魔術方法     執行__new__()後,接受到__new__()方法返回的地址,並給對象賦值地址,再執行__init__()方法

觸發時機:初始化對象時觸發(不是實例化觸發,但是和實例化在一個操作中)

 

__new__:實例化的魔術方法    先執行__new__(),向內存申請空間,並返回開闢的地址

觸發時機:在實例化對時觸發

 

__call__:調用對象的魔術方法

觸發時機:將對象當作函數調用時觸發  對象()

會默認調用此函數中的內容

 

__del__: delete縮寫  析構魔術方法

觸發時機:當對象沒有用(沒有任何變量引用)的時候被觸發

1、對象賦值

tp = TestPhone()

tp1 = tp  說明:tp和tp1共同指向同一個地址

2、刪除地址的引用

del p1    刪除p1對地址的引用

3、查看對地址的引用次數

import sys

sys.getrefcount(tp)

4、當一塊空間沒有任何引用(地址指向),默認執行__del__()

 

當執行代碼最後, python解釋器,回收所有在本次執行過程中使用到的空間

垃圾回收機制:python底層自帶,內存釋放
 

__str__:單純打印對象名稱

觸發時機:打印對象名,自動觸發調用__str__裏面的內容

print(對象)

 

注意:一定要在__str__方法中添加return,return後面的內容就是打印對象看到的內容


 

總結:魔術方法

重點:

__init__  構造方法,創建完空間之後調用的第一個方法

__str__   打印對象的名稱

 

瞭解:

__new__  作用:開闢空間

__del__  作用:沒有指針引用的時候會調用,99%都不需要重寫

__call__ 作用:是否將對象當成函數用

 

總結:

方法:

普通方法

    def 方法名(self, 參數...):

        pass

    對象.普通方法()

 

    方法之間的調用:

    class A:

        def a(self):

            pass

 

        def b(self):

            #調用a方法

            self.a()

 

類方法:

    @classmethod

    def 方法名(cls, 參數...):

        pass

    類名.方法名()

    對象.方法名()

 

靜態方法:

    @staticmethod

    def 方法名(參數...):

        pass

    類名.方法名()

    對象.方法名()

 

魔術方法:

自動執行的方法

print(對象) --->  __str__

 

代碼部分:

import sys

class TestPhone:
    #函數 和 類裏面定義的  方法
    __size = 20  #私有變量
    brand = "info"

    #魔術方法之一
    #init 初始化
    def __init__(self, brand): #獲取new中的地址,給對象賦值地址
        print("------> init", self)
        self.brand = brand
        # self.price = price
        # self.p_type = 'mate 30'

    #向內存要空間  -->地址
    def __new__(cls, brand): #*args, **kwargs  #先執行new方法,new新開闢空間(開闢內存)
        print("------> new")
        position = object.__new__(cls)  #申請內存開闢空間,獲取開闢的地址
        print(position)
        return position  #地址

    #調用方式: 對象()
    def __call__(self, *args, **kwargs):
        print("------> call ")
        print("執行對象得到參數是:", args)  #輸出:('aaa',)

    #單純打印對象名稱,出來的是地址。地址對於開發者來說沒有太大意義
    #如果想在打印對象名的時候,能夠給開發者更多的信息量,
    def __str__(self):
        print("------> str")
        return self.brand    #此時對象名稱爲 brand屬性的名稱

    #del 對象
    def __del__(self):
        print("------> delete")

    # def cus_call(self):  #self是不斷髮生改變
    #     print("價格", self.price)   #不能保證每個self中都存在price

    #類裏面的方法 依賴於對象,self爲對象的地址
    def call(self):    #自己
        print('self--->', self)

    #類方法     傳的參數不是對象,是類  cls-->對應TestPhone類
    @classmethod
    def test(cls):
        print(cls)  #<class '__main__.TestPhone'>
        # print(cls.brand)  報錯
    
    @classmethod
    def update_size(cls):
        __size = 50
        print("尺寸爲:", __size)

    def obj_test(self):
        print("object info method")
        self.test()  #類中方法的調用,需要self.方法名

    @staticmethod
    def s_test():
        print("------> 靜態方法")
        # print(self.brand) #語法錯誤
        print(TestPhone.__size)

# tp = TestPhone('huawei', 5999)
# tp.cus_call()

# tp2 = TestPhone('xiaomi', 3999)
# tp2.cus_call()
# tp2.test()

#調用類方法
TestPhone.update_size()

#調用靜態方法
TestPhone.s_test()

tp = TestPhone('huawei')
print(tp.brand)

tp('aaa')

tp.brand = 'test'

tp1 = tp
print(tp1.brand)

tp2 = tp
print(tp2.brand)

print("*" * 20)
print(tp)  #調用__str__
print("--->", tp.brand)

#斷掉tp1、tp2的引用
del tp1
del tp2

print(sys.getrefcount(tp))  #獲取對象的引用個數,調用這個函數也算一個

 

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章