學習筆記(11月07日)--類

四周二次課(11月7日)


一、 類的重寫

1.1 重寫一般方法

class A:
    def hello(self):
        print('Hello,i am A.')
class B(A):
    pass
a = A()
b = B()
a.hello()
b.hello()

結果:

Hello,i am A.
Hello,i am A.

解釋:

B類沒有定義自己的hello方法,故當hello被調用時,原始信息就被打印出來了。

B類也可以重寫這個hello方法

class A:
    def hello(self):
        print('Hello,i am A.')
class B(A):
    def hello(self):  
        print('Hello,i am B.')
a = A()
b = B()
a.hello()
b.hello()

結果:

Hello,i am A.
Hello,i am B.

1.2 重寫特殊的構造方法

1、調用未綁定的基類構造方法

class Bird:
    def __init__(self):
        self.hungry = True
    def eat(self):
        if self.hungry:
            print('Aaaah...')
            self.hungry = False
        else:
            print('No,thanks!')
class SongBird(Bird):
    def __init__(self):
            Bird.__init__(self)
            self.sound = 'Squawk!'
    def sing(self):
        print(self.sound)
b = SongBird()
b.sing()
b.eat()
b.eat()

結果:

Squawk!
Aaaah...
No,thanks!


2、使用super函數

class Bird():
    def __init__(self):
        self.hungry = True
    def eat(self):
        if self.hungry:
            print('Aaaah...')
            self.hungry = False
        else:
            print('No,thanks!')
class SongBird(Bird):
    def __init__(self):
        super(SongBird,self).__init__()
        self.sound = 'Squawk!'
    def sing(self):
        print(self.sound)
b = SongBird()
b.sing()
b.eat()
b.eat()

結果:

Squawk!
Aaaah...
No,thanks!

解釋:

Python 2中定義類需要寫上object,否則報錯。


二、類的私有變量

在Python中可以通過在屬性變量名前加上雙下劃線定義屬性爲私有屬性

特殊變量命名


1、 _xx 以單下劃線開頭的表示的是protected類型的變量。即保護類型只能允許其本身與子類進行訪問。若內部變量標示,如: 當使用“from M import”時,不會將以一個下劃線開頭的對象引入 。


2、 __xx 雙下劃線的表示的是私有類型的變量。只能允許這個類本身進行訪問了,連子類也不可以用於命名一個類屬性(類變量),調用時名字被改變(在類FooBar內部,__boo變成_FooBar__boo,如self._FooBar__boo)


3、 __xx__定義的是特殊方法。用戶控制的命名空間內的變量或是屬性,如init , __import__或是file 。只有當文檔有說明時使用,不要自己定義這類變量。 (就是說這些是python內部定義的變量名)


在這裏強調說一下私有變量,python默認的成員函數和成員變量都是公開的,沒有像其他類似語言的public,private等關鍵字修飾.但是可以在變量前面加上兩個下劃線"_",這樣的話函數或變量就變成私有的.這是python的私有變量軋壓(這個翻譯好拗口),英文是(private name mangling.) **情況就是當變量被標記爲私有後,在變量的前端插入類名,再類名前添加一個下劃線"_",即形成了_ClassName__變量名.**


Python內置類屬性

__dict__ : 類的屬性(包含一個字典,由類的數據屬性組成)

__doc__ :類的文檔字符串

__module__: 類定義所在的模塊(類的全名是'__main__.className',如果類位於一個導入模塊mymod中,那麼className.__module__ 等於 mymod)

__bases__ : 類的所有父類構成元素(包含了一個由所有父類組成的元組)


例子1:

class A(object):
   def __init__(self):
       self.__data = []  # 翻譯成 self._A__data=[]

   def add(self, item):
       self.__data.append(item)  # 翻譯成 self._A__data.append(item)

   def printData(self):
       print self.__data  # 翻譯成 self._A__data


a = A()
a.add('hello')
a.add('python')
a.printData()
# print a.__data  #外界不能訪問私有變量 AttributeError: 'A' object has no attribute '__data'
print a._A__data  # 通過這種方式,在外面也能夠訪問“私有”變量;這一點在調試中是比較有用的!

結果:

['hello', 'python']
['hello', 'python']


例子2:

class A():
    def __init__(self):
        self.__name = 'python'  # 私有變量,翻譯成 self._A__name='python'

    def __say(self):  # 私有方法,翻譯成 def _A__say(self)
        print self.__name  # 翻譯成 self._A__name


a = A()
# print a.__name #訪問私有屬性,報錯!AttributeError: A instance has no attribute '__name'
print a.__dict__  # 查詢出實例a的屬性的集合
print a._A__name  # 這樣,就可以訪問私有變量了
# a.__say()#調用私有方法,報錯。AttributeError: A instance has no attribute '__say'
print dir(a)  # 獲取實例的所有屬性和方法
a._A__say()  # 這樣,就可以調用私有方法了

結果:

{'_A__name': 'python'}
python
['_A__name', '_A__say', '__doc__', '__init__', '__module__']
python


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