Python面向?qū)ο缶幊?/h2>

1.1類和對象

1.1.1萬物皆對象

分類是人們認識世界的一個很自然的過程,在日常生活中會不自覺地將對象進行進行分類

對象歸類
  • 類是抽象的概念,僅僅是模板 比如說:“人”
  • 對象是一個你能夠看得到、摸得著的具體實體: 趙本山,劉德華,趙麗穎
舉例
user1 = 'zhangsan'
print(type(user1))
user2 = 'lisi'
print(type(user2))

輸出

<class 'str'>
<class 'str'>

以上str是類(python中的字符串類型),user1和user2是對象(以前我們叫變量)

研究對象

顧客類型

屬性:
姓名—張浩
年齡—20
體重—60kg
行為:
購買商品

收銀員類型

屬性:
員工號—10001
姓名—王淑華
部門—財務(wù)部

行為:
收款
打印賬單

1.1.2 對象的特征——屬性

屬性——對象具有的各種特征。 每個對象的每個屬性都擁有特定值。 例如:顧客張浩和李明的年齡、姓名不一樣。

1.1.4 對象的特征——方法(操作,行為)

方法——對象執(zhí)行的操作(通常會改變屬性的值)。 顧客對象的方法---購買商品。 收銀員對象的方法----收款。

對象:用來描述客觀事物的一個實體,由一組屬性和方法構(gòu)成

例子

image

類型:狗
對象名:doudou
屬性:
顏色:白色
方法:
叫,跑,吃

對象同時具有屬性和方法兩項特性。 對象的屬性和方法通常被封裝在一起,共同體現(xiàn)事物的特性, 二者相輔相承,不能分割。

1.1.4 從對象抽象出“類”

抽取出下列對象的共同特征(屬性和方法)

類是模子,定義對象將會擁有的特征(屬性)和行為(方法)。

再次強調(diào)

  • 類是抽象的概念,僅僅是模板。 比如說:“人”, 類定義了人這種類型屬性(name,age...)和方法(study,work...)。
  • 對象是一個你能夠看得到、摸得著的具體實體: 趙本山,劉德華,趙麗穎,這些具體的人都具有人類型中定義的屬性和方法,不同的是他們各自的屬性不同。

根據(jù)類來創(chuàng)建對象被稱為實例化。

1.2 類的定義

1.2.1 定義只包含方法的類

在 Python 中要定義一個只包含方法的類,語法格式如下:

class 類名:

    def 方法1(self, 參數(shù)列表):
        pass

    def 方法2(self, 參數(shù)列表):
        pass

方法 的定義格式和之前學(xué)習過的函數(shù) 幾乎一樣。 區(qū)別在于第一個參數(shù)必須是 self。

1.2.2 創(chuàng)建對象

當一個類定義完成之后,要使用這個類來創(chuàng)建對象,語法格式如下:

對象變量 = 類名()

第一個面向?qū)ο蟪绦?/p>

需求:

  • 小貓 愛 吃 魚,小貓 要 喝 水。

分析:

  • 定義一個貓類Cat。
  • 定義兩個方法 eatdrink。
class Cat:
    """這是一個貓類"""

    def eat(self):
        print("小貓愛吃魚")

    def drink(self):
        print("小貓在喝水")

tom = Cat()
tom.drink()
tom.eat()

使用 Cat 類再創(chuàng)建一個對象

lazy_cat = Cat()
lazy_cat.eat()
lazy_cat.drink()

1.3 self 參數(shù)

我們在調(diào)用對象的方法是不需要傳遞self參數(shù),這個self參數(shù)是系統(tǒng)自動傳遞到方法里的。

1.3.1 給對象增加屬性

在 Python 中,要 給對象設(shè)置屬性,非常的容易,但是不推薦使用。 因為:對象屬性的封裝應(yīng)該封裝在類的內(nèi)部。 要 給對象設(shè)置屬性,只需要在 類的外部的代碼 中直接通過.設(shè)置一個屬性即可

tom.name = "Tom"
lazy_cat.name = "大懶貓"

1.3.2 理解self到底是什么

class Cat:
    """這是一個貓類"""

    def eat(self):
        print(f"小貓愛吃魚,我是{self.name},self的地址是{id(self)}")

    def drink(self):
        print("小貓在喝水")

tom = Cat()
print(f'tom對象的id是{id(tom)}')
tom.name = "Tom"
tom.eat()
print('-'*60)
lazy_cat = Cat()
print(f'lazy_cat對象的id是{id(lazy_cat)}')
lazy_cat.name = "大懶貓"
lazy_cat.eat()

輸出

tom對象的id是36120000
小貓愛吃魚,我是Tom,self的地址是36120000
------------------------------------------------------------
lazy_cat對象的id是36120056
小貓愛吃魚,我是大懶貓,self的地址是36120056

由輸出可見,當我們使用的時候,python會自動將x對象做為實參傳給x方法的self參數(shù)。 也可以這樣記憶,誰點(.)的方法,self就是誰。

x對象.x方法()

類中的每個實例方法的第一個參數(shù)都是self

1.4 初始化方法init()

初始化方法

  • 當使用 類名()創(chuàng)建對象時,會自動 執(zhí)行以下操作:
    1.為對象在內(nèi)存中 分配空間 —— 創(chuàng)建對象(調(diào)用__new__
    2.為對象的屬性 設(shè)置初始值 —— 初始化方法(調(diào)用__init__并且將第一步創(chuàng)建的對象,通過self參數(shù)傳給__init__)
  • 這個 初始化方法 就是__init__方法,__init__是對象的內(nèi)置方法(有的書也叫魔法方法,特殊方法)

__init__方法是 專門 用來定義一個類 具有哪些屬性并且給出這些屬性的初始值的方法!

Cat 中增加__init__方法,驗證該方法在創(chuàng)建對象時會被自動調(diào)用

class Cat:
    """這是一個貓類"""

    def __init__(self):
        print("初始化方法")
  • 在初始化方法內(nèi)部定義屬性

__init__方法內(nèi)部使用 self.屬性名 = 屬性的初始值 就可以 定義屬性
定義屬性之后,再使用 Cat類創(chuàng)建的對象,都會擁有該屬性

class Cat:

    def __init__(self):

        print("這是一個初始化方法")

        # 定義用 Cat 類創(chuàng)建的貓對象都有一個 name 的屬性
        self.name = "Tom"

    def eat(self):
        print("%s 愛吃魚" % self.name)

# 使用類名()創(chuàng)建對象的時候,會自動調(diào)用初始化方法 __init__
tom = Cat()

tom.eat()

改造初始化方法 —— 初始化的同時設(shè)置初始值

  • 在開發(fā)中,如果希望在 創(chuàng)建對象的同時,就設(shè)置對象的屬性,可以對 __init__方法進行 改造
  1. 把希望設(shè)置的屬性值,定義成__init__方法的參數(shù)
  2. 在方法內(nèi)部使用 self.屬性 = 形參 接收外部傳遞的參數(shù)
  3. 在創(chuàng)建對象時,使用 類名(屬性1, 屬性2...) 調(diào)用
class Cat:

    def __init__(self, name):
        print("初始化方法 %s" % name)
        self.name = name

tom = Cat("Tom")

lazy_cat = Cat("大懶貓")

1.5_str_ 方法

在 Python 中,使用 print 輸出 對象變量,默認情況下,會輸出這個變量的類型,以及 在內(nèi)存中的地址(十六進制表示)

class Cat:

    def __init__(self, new_name):

        self.name = new_name

        print("%s 來了" % self.name)

tom = Cat("Tom")
print(tom)

輸出

Tom 來了
<__main__.Cat object at 0x0000000002852278>

如果在開發(fā)中,希望使用 print 輸出 對象變量 時,能夠打印 自定義的內(nèi)容,就可以利用 __str__ 這個內(nèi)置方法了

注意:__str__方法必須返回一個字符串

class Cat:

    def __init__(self, new_name):

        self.name = new_name

        print("%s 來了" % self.name)


    def __str__(self):
        return "我是小貓:%s" % self.name

tom = Cat("Tom")
print(tom)
Tom 來了
我是小貓:Tom

1.6 面向?qū)ο髒s面向過程

class Car:
    def __init__(self,type,price):
        self.type = type
        self.price = price
        self.distance = 0 #新車

    def printCarInfo(self):
        print ("the car's Info in class:type %s,price:%d"%(self.type,self.price))

    def driveDistance(self,distance):
        self.distance += distance
        self.price -= distance*10

print(f'面向?qū)ο?)
carOne = Car('passat',250000)
carOne.printCarInfo()
carOne.driveDistance(100)
carOne.driveDistance(200)
print(f'passat已經(jīng)行駛了{carOne.distance}公里')
print(f'passat的價格是{carOne.price}')

輸出

面向?qū)ο?the car's Info in class:type passat,price:250000
passat已經(jīng)行駛了300公里
passat的價格是247000

小結(jié) 可以拿公司運營作為比喻來說明面向?qū)ο箝_發(fā)方式的優(yōu)點

外部調(diào)用代碼好比老板 面向過程中函數(shù)好比員工,讓員工完成一個任務(wù),需要老板不斷的干涉,大大影響了老板的工作效率。 面向?qū)ο笾袑ο蠛帽葐T工,讓員工完成一個任務(wù),老板只要下命令即可,員工可以獨擋一面,大大節(jié)省了老板的時間

還有一種說法

世界上本沒有類,代碼寫多了,也就有了類

面向?qū)ο箝_發(fā)方式是晚于面向過程方式出現(xiàn)的,幾十年前,面向?qū)ο筮€沒有出現(xiàn)以前,很多軟件系統(tǒng)的代碼量就已經(jīng)達到幾十上百萬行,科學(xué)家為了組織這些代碼,將各種關(guān)系密切的數(shù)據(jù),和相關(guān)的方法分門別類,放到一起管理,就形成了面向?qū)ο蟮拈_發(fā)思想和編程語言語法。

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

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

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