Python學習之面向對象編程

Python學習目錄java

  1. 在Mac下使用Python3
  2. Python學習之數據類型
  3. Python學習之函數
  4. Python學習之高級特性
  5. Python學習之函數式編程
  6. Python學習之模塊
  7. Python學習之面向對象編程
  8. Python學習之面向對象高級編程
  9. Python學習之錯誤調試和測試
  10. Python學習之IO編程
  11. Python學習之進程和線程
  12. Python學習之正則
  13. Python學習之經常使用模塊
  14. Python學習之網絡編程

面向對象編程——Object Oriented Programming,簡稱OOP,是一種程序設計思想。OOP把對象做爲程序的基本單元,一個對象包含了數據和操做數據的函數。python

類和實例

定義

class Student(object):
    pass

stone = Student()
stone.name = "stone"
stone.age = 2

print(stone.name, stone.age)
複製代碼

上面代碼中:編程

  • class後面緊接的是類名,類名以大寫字母開頭
  • (object)是該類從哪一個類繼承下來的
  • 使用時候能夠自由的給實例變量綁定屬性

方法

class Student(object):
    def __init__(self, name, age):
        self.name = name
        self.age = age

    def print_info(self):
        print(self.name, self.age)
        
stone = Student("stone", 18)
stone.print_info()
複製代碼

上面代碼中:api

  • __init__方法的第一個參數永遠是self,表示建立的實例自己,所以,在__init__方法內部,就能夠把各類屬性綁定到self,由於self就指向建立的實例自己。相似於java的構造函數。
  • 定義一個方法,除了第一個參數是self外,其餘和普通函數同樣。要調用一個方法,只須要在實例變量上直接調用,除了self不用傳遞,其餘參數正常傳入。

訪問限制

  • 實例的變量名若是以__開頭,就變成了一個私有變量(private),只有內部能夠訪問,外部不能訪問。
  • 變量名相似__xxx__的,也就是以雙下劃線開頭,而且以雙下劃線結尾的,是特殊變量,特殊變量是能夠直接訪問的,不是private變量。

繼承和多態

在OOP程序設計中,當咱們定義一個class的時候,能夠從某個現有的class繼承,新的class稱爲子類(Subclass),而被繼承的class稱爲基類、父類或超類(Base class、Super class)。和java同樣。網絡

靜態語言 vs 動態語言:ssh

對於靜態語言(例如Java)來講,若是須要傳入Animal類型,則傳入的對象必須是Animal類型或者它的子類,不然,將沒法調用Animal中的方法。對於Python這樣的動態語言來講,則不必定須要傳入Animal類型。咱們只須要保證傳入的對象有Animal中的方法就能夠了。函數式編程

對象信息

使用type()

>>> import types
>>> def fn():
...     pass
...
>>> type(fn)==types.FunctionType
True
>>> type(abs)==types.BuiltinFunctionType
True
>>> type(lambda x: x)==types.LambdaType
True
>>> type((x for x in range(10)))==types.GeneratorType
True
複製代碼

以上代碼能夠看出,判斷基本數據類型能夠直接寫intstr等,但若是要判斷一個對象是不是函數怎麼辦?能夠使用types模塊中定義的常量。函數

使用isinstance()

>>> isinstance([1, 2, 3], (list, tuple))
True
>>> isinstance((1, 2, 3), (list, tuple))
Tru
複製代碼

能夠判斷一個變量是不是某些類型中的一種,好比上面的代碼就能夠判斷是不是list或者tuplepost

使用dir()

若是要得到一個對象的全部屬性和方法,能夠使用dir()函數,它返回一個包含字符串的list,好比,得到一個str對象的全部屬性和方法:學習

>>> dir('ABC')
['__add__', '__class__',..., '__subclasshook__', 'capitalize', 'casefold',..., 'zfill']
複製代碼

相似__xxx__的屬性和方法在Python中都是有特殊用途的,好比__len__方法返回長度。在Python中,若是你調用len()函數試圖獲取一個對象的長度,實際上,在len()函數內部,它自動去調用該對象的__len__()方法,因此,下面的代碼是等價的:

>>> len('ABC')
3
>>> 'ABC'.__len__()
3
複製代碼

咱們本身寫的類,若是也想用len(myObj)的話,就本身寫一個__len__()方法:

>>> class MyDog(object):
...     def __len__(self):
...         return 100
...
>>> dog = MyDog()
>>> len(dog)
100
複製代碼

僅僅把屬性和方法列出來是不夠的,配合getattr()setattr()以及hasattr(),咱們能夠直接操做一個對象的狀態:

>>> class MyObject(object):
...     def __init__(self):
...         self.x = 9
...     def power(self):
...         return self.x * self.x
...
>>> obj = MyObject()
複製代碼

緊接着,能夠測試該對象的屬性:

>>> hasattr(obj, 'x') # 有屬性'x'嗎?
True
>>> obj.x
9
>>> hasattr(obj, 'y') # 有屬性'y'嗎?
False
>>> setattr(obj, 'y', 19) # 設置一個屬性'y'
>>> hasattr(obj, 'y') # 有屬性'y'嗎?
True
>>> getattr(obj, 'y') # 獲取屬性'y'
19
>>> obj.y # 獲取屬性'y'
19
複製代碼

也能夠得到對象的方法:

>>> hasattr(obj, 'power') # 有屬性'power'嗎?
True
>>> getattr(obj, 'power') # 獲取屬性'power'
<bound method MyObject.power of <__main__.MyObject object at 0x10077a6a0>>
>>> fn = getattr(obj, 'power') # 獲取屬性'power'並賦值到變量fn
>>> fn # fn指向obj.power
<bound method MyObject.power of <__main__.MyObject object at 0x10077a6a0>>
>>> fn() # 調用fn()與調用obj.power()是同樣的
81
複製代碼

實例屬性和類屬性

類自己須要綁定一個屬性:

class Student(object):
    name = 'Student'
複製代碼

當咱們定義了一個類屬性後,這個屬性雖然歸類全部,但類的全部實例均可以訪問到。來測試一下:

>>> class Student(object):
...     name = 'Student'
...
>>> s = Student() # 建立實例s
>>> print(s.name) # 打印name屬性,由於實例並無name屬性,因此會繼續查找class的name屬性
Student
>>> print(Student.name) # 打印類的name屬性
Student
>>> s.name = 'Michael' # 給實例綁定name屬性
>>> print(s.name) # 因爲實例屬性優先級比類屬性高,所以,它會屏蔽掉類的name屬性
Michael
>>> print(Student.name) # 可是類屬性並未消失,用Student.name仍然能夠訪問
Student
>>> del s.name # 若是刪除實例的name屬性
>>> print(s.name) # 再次調用s.name,因爲實例的name屬性沒有找到,類的name屬性就顯示出來了
Student
複製代碼

下一篇:Python學習之面向對象高級編程

相關文章
相關標籤/搜索