天天看點

Python面向對象程式設計

什麼是類和對象?

python中,一切皆為對象,比如人就是一個對象,汽車、房子都是對象。

每一個對象都有自己的屬性,比如人這個對象的屬性有性别、身高、年齡等等

房子的屬性有房價、面積、戶型等等

在python中,一個對象的特征也稱為屬性(attribute)。它所具有的行為也稱為方法(method)

是以:對象=屬性+方法

在python中,我們把具有相同屬性和方法的對象歸為一個類(class)

比如:人、動物、植物、建築等等

類是對象的模闆和藍圖,對象是類的執行個體化。類不代表具體的事物,而對象表示具體的事物。

注意:屬性為對象所有,類不具有對象的屬性!!!

初始化對象:

建立類時,可以定義一個特定的方法為__init__()。隻要建立類的執行個體,就會運作該方法。可以向

__init__()方法傳遞參數,這樣可以在執行個體化對象時,把屬性設定為你希望的值

例如:

1

2

3

4

5

6

7

8

9

10

11

12

13

14

15

16

17

<code>#!/usr/bin/env python</code>

<code>#-*-coding:utf-8-*-</code>

<code>class person:</code>

<code>    </code><code>def __init__(self,name,age):</code>

<code>        </code><code>self.name = name</code>

<code>        </code><code>self.age = age</code>

<code>        </code><code>#self.__private = flag</code>

<code>    </code><code>def action(self):</code>

<code>        </code><code>return</code> <code>self.name +</code><code>' 在上班'</code>

<code>p1 = person(</code><code>'laowang'</code><code>,50)</code>

<code>print p1.name</code>

<code>print p1.age</code>

<code>輸出結果:</code>

<code>laowang</code>

<code>50</code>

什麼是靜态字段和動态字段?

上面的self是什麼?Name、Age是什麼?name、age又是什麼?

self是建立對象的值,也就是說它表示對象本身,在上面的例子中self就是p1,而Name、Age是對象的屬性,這種屬于對象的字段叫做動态字段。name、age是建立對象時需要傳遞的參數。

上面的例子中memo是什麼?它屬于類還是某一個對象?

memo屬于類,這種屬于類的字段通常被稱為靜态字段。self.xx才是屬于對象的

屬于類的字段,靜态字段使用類名.字段名來通路,例如上例中 person.memo

動态字段使用對象名.字段名,例如上例中p1.Name、p1.Age

類能否通路動态字段?對象能否通路靜态字段?

類不能通路動态字段,因為動态字段是對象的一個屬性,隻屬于對象。對象可以通路靜态字段。通路方法:對象名.靜态字段名,在前面的例子中為 

<code>    </code><code>memo = </code><code>'我是靜态字段'</code>

<code>print person.memo</code>

輸出結果:

<code>我是靜态字段</code>

注意:為了避免歧義,盡量避免對象通路靜态字段

什麼是靜态方法和動态方法?

在最開始,我們說過

對象=屬性+方法

那麼什麼是方法?

方法就是對象的一個行為,在python中方法就是一個函數,它可以被對象所調用,對象調用方法的可以這樣寫:對象名.方法名,

<code>print p1.action()</code>

<code>laowang 在上班</code>

上例中action(self)這種帶有參數的方法叫動态方法,動态方法隻能被對象通路,而不能被類通路。

有了動态方法則也有靜态方法,那麼如果定義一個靜态方法?

定義一個靜态方法,有兩個要求:

1、需要在動态方法上加一個裝飾器“@staticmethod”

2、去掉self,因為靜态方法屬于類,而self屬于對象

建立靜态方法:

<code>@staticmethod</code>

<code>def foo():</code>

<code>    </code><code>print </code><code>'這是一個靜态方法'</code>

<code>    </code><code># #靜态字段</code>

<code>    </code><code># memo = '衆多物種之一'</code>

<code>    </code><code># #__init__函數用來對類進行執行個體化</code>

<code>    </code><code>def __init__(self,name,age,male):</code>

<code>        </code><code>pass</code>

<code>    </code><code>#靜态方法</code>

<code>    </code><code>@staticmethod</code>

<code>    </code><code>def static():</code>

<code>        </code><code>return</code> <code>"這是一個靜态方法"</code>

<code>print person.static()</code>

<code>這是一個靜态方法</code>

總結:靜态方法和動态方法的差別

靜态方法能被類和對象通路,而動态方法隻能被對象通路。靜态方法需要@staticmethod裝飾器修飾,并且不帶有self

什麼是特性(property)?

特性是字段和方法之外的一個定義,他不同于字段和方法,通常用來傳回值,特性能被對象調用,

調用方法:對象名.方法名  注意方法名後面沒有括号

如果定義一個特性?

在動态方法上加一個裝飾器@property

<code>@property</code>

<code>def bar(self):</code>

<code>    </code><code>return</code> <code>self.Name</code>

靜态方法什麼情況下使用?

場景:假設我們需要操作資料庫,會執行增删改查動作,每一個動作就是一個方法,如果使用動态方法,那麼每一次查詢需要建立一個對象,每一次修改需要建立一個對象,如果使用靜态方法,則不需要建立多個對象了。因為靜态方法可以使用類.靜态方法來通路。

其實靜态方法和一個普通的函數沒有什麼差別。用的也并不多。Python是一個子產品化的語言,為了面向對象程式設計,才弄出一個和其他語言一樣的靜态方法出來。這是曆史遺留問題。

私有字段和私有方法

如何定義私有字段?

定義私有字段時,使用self.__name = name的方式,即在字段名前面加兩個下劃線。

私有字段能夠被對象通路?

預設情況下,私有字段不能直接被對象通路。

<code>    </code><code>def __init__(self,name,age,flag):</code>

<code>        </code><code>#私有字段</code>

<code>        </code><code>self.__heigtht = flag</code>

<code>p1 = person(</code><code>'laowang'</code><code>,50,True)</code>

<code>#print p1.name</code>

<code>print p1.__height</code>

<code>Traceback (most recent call last):</code>

<code>  </code><code>File </code><code>"C:/Users/zenge/PycharmProjects/2/day4/.py"</code><code>, line 17, </code><code>in</code> <code>&lt;module&gt;</code>

<code>    </code><code>print p1.__height</code>

<code>AttributeError: person instance has no attribute </code><code>'__height'</code>

如何使私有字段被對象通路?

私有字段隻有被定義到方法中,并return出來然後使用對象.方法的方式才能通路

還是上面的例子,我們修改下

<code>    </code><code>def show(self):</code>

<code>        </code><code>return</code> <code>self.__heigtht</code>

<code>print p1.show()</code>

<code>True</code>

是以,要通路私有字段,必須将私有字段定義成一個通路,并return這個字段。

我們還可以使用@property來擷取私有字段

18

19

20

<code>    </code><code>@property</code>

<code>    </code><code>def foo(self):</code>

<code>print p1.foo</code>

私有方法

如何定義一個私有方法?

在方法名前面加加兩個下劃線即可。

私有方法能否直接被對象通路呢?

看下面的例子

<code>    </code><code>#私有方法</code>

<code>    </code><code>def __sha(self):</code>

<code>        </code><code>return</code> <code>'我是私有方法'</code>

<code>print p1.__sha()</code>

<code>  </code><code>File </code><code>"C:/Users/zenge/PycharmProjects/2/day4/.py"</code><code>, line 25, </code><code>in</code> <code>&lt;module&gt;</code>

<code>    </code><code>print p1.sha()</code>

<code>AttributeError: person instance has no attribute </code><code>'__sha'</code>

如何使私有方法被對象通路?

我們可以通過定義一個公有方法,在這個公有方法中return私有方法,這樣對象就可以使用對象.方法的方式通路私有方法啦

21

<code>    </code><code>def public(self):</code>

<code>print p1.public()</code>

輸出結果

私有字段和私有方法什麼情況下使用?

私有字段和私有方法是不能被外部調用的,隻有在你定義的類裡面被調用,是以如果你不想某個方法或者字段被外部調用時,就可以使用私有方法和私有方法,例如你寫的接口的中的賬号密碼等字段。

前面有介紹如何調用私有字段和私有方法,但是不建議這個做,

如何修改私有字段?

前面介紹了私有字段預設不能被通路,但是可以通過@property特性來使私有字段被通路,那麼私有字段如何能被修改呢?

要修改私有字段,需要對傳回私有字段的函數添加裝飾器。并且在類名後面加(object)

例如

22

23

24

25

26

<code>class person(object):</code>

<code>        </code><code>self.__height = flag</code>

<code>        </code><code>return</code> <code>self.__height</code>

<code>    </code><code>#隻讀私有字段</code>

<code>    </code><code>#修改私有字段,需要加參數</code>

<code>    </code><code>@foo.setter</code>

<code>    </code><code>def foo(self,value):</code>

<code>         </code><code>self.__height = value</code>

<code>p1.foo = False</code>

<code>False</code>

本文轉自 曾哥最愛 51CTO部落格,原文連結:http://blog.51cto.com/zengestudy/1857953,如需轉載請自行聯系原作者