1. 程式人生 > 其它 >面向物件微講解(三)

面向物件微講解(三)

面向物件微講解(三)

面向物件三大特徵之封裝

  1. 封裝的含義

	封裝就是將類中的某些名字'隱藏'起來,不想讓外界直接呼叫,但是呢又提供了專門的通道去訪問,可以在通道內新增額外
的功能。這個通道呢就是我們經常說的介面,將資料隱藏起來就限制了類外部對資料的直接操作,類外部想要操作資料就需要使用類
內提供的相應的介面來間接的操作資料,介面之上我們就可以新增額外的邏輯來限制資料的操作。
    那怎麼才是封裝呢,或者說怎麼封裝名字呢?
    在類中想要封裝一個名字,只需要在該名字的前面加上兩個下劃線,但是注意一下只有在類的定義階段封裝的功能才能生效。雖
然我們是封裝了起來,但是並不是絕對的,只是改變了語法,給它做了一個變形,並不是我們看上去的那樣。
  1. 封裝的簡單操作

# class Student:
#     # 對school資料進行了封裝
#     __school = '復旦大學'
#     def Teacher(self):
#         pass

# obj = Student()
# print(obj.__school)  # 執行發現報錯了,報錯說類中沒有__school這個資料,可是我們寫了的,這就是封裝,不能直接操作
資料
# 我們剛剛已經講過封裝只是改變了語法,給它做了一個變形
# print(Student.__dict__)  # _Student__school 我們封裝的名字變成了這樣
# print(obj._Student__school)  # 復旦大學 我們直接使用這個是可以的
# 我們是不能直接這樣使用這個名字,因為我們封裝起來就是為了外部不能直接操作資料的
class Student:
    # 對school資料進行了封裝
    __school = '復旦大學'

    def __init__(self,name,age):
        self.__name = name
        self.__age = age

    # 設定一個專門訪問資料的通道或者說介面
    def check_name(self):
        print(self.__name)

    # 設定一個專門訪問資料的通道或者說介面
    def check_age(self):
        print(self.__age)
    # 設定一個專門訪問資料的通道或者說介面,還可以做一些額外的操作
    def check_info(self):
        print('名字:%s 年齡:%s'% (self.__name,self.__age))
    def check(self):
        if self.__name == 'oscar':
            print('%s大人你好'%self.__name)
        if self.__age == 21:
            print('生日快樂')

obj = Student('oscar',21)
obj.check_name()  # oscar
obj.check_age()  # 21
obj.check_info()  # 名字:oscar 年齡:21
obj.check()  # oscar大人你好  生日快樂
  1. 偽裝(property)

	property偽裝就是將方法偽裝成資料,有時候很多資料都是經過計算獲得,這些資料的計算應該資料而不是功能,比如
BMI指數,應該屬於人的資料而不是人的功能。
    class Person():
    def __init__(self,name,height,weighe):
        self.__name = name
        self.__height = height
        self.__weight = weighe

    @property
    def BMI(self):
        print('%s的BMI指數為%s'% (self.__name,self.__weight / self.__height ** 2))

obj = Person('oscar', 1.78,80)
# obj.BMI()
'''
發現會有一個報錯資訊說不具備呼叫括號的能力,可是我們寫的就是一個方法
方應該是具備呼叫括號的能力的,因為我們加了一個語法糖@property,進行了偽裝
把方法偽裝成了資料,呼叫資料的時候是不需要加括號的
'''
obj.BMI  # oscar的BMI指數為25.24933720489837

面向物件三大特性之多型

  1. 多型的含義

	多型就是一種事物的多種形態,比如說水就有固態、液態、氣態,這三種形態可以統稱為水,比如說動物,貓是動
物、狗是動物、雞是動物,這是動物的多種形態。
    多型呢是一種程式設計思想,偏向於理論。我們來舉個例子:人可以分為白種人、黑種人、黃種人,他們都有說話的能力,不
可能就因為膚色不一樣就不能說話了,我們定義一個Person類,類裡面有一個speak方法,然後我們再來定義三個子類來繼承
Person類,這三個子類分別是White_person、Black_person、Yellow_person類,每一個子類都有自己關於說話的方法,
但是各不相同,這樣我們來用的時候就有點麻煩,所以呢我們就可以利用多型的思想,每個子類的的關於說話的方法其本質就
是關於說話的不同的表現形式,那我們把所有關於說話的方法都定義為同一個名字,這樣的好處就在於增強了程式的靈活性和
可擴充套件性。
	多型性是有一個鴨子型別理論的:只要看著像鴨子、走路像鴨子、說話像鴨子,那麼就是鴨子。
  1. 多型簡單演示

class Person:
    def speak(self):
        pass
class White_person(Person):
    def speak(self):
        print('白種人說話的方法')
class Black_person(Person):
    def speak(self):
        print('黑種人說話的方法')
class Yellow_person(Person):
    def speak(self):
        print('黃種人說話的方法')

bai = White_person()
hei = Black_person()
huang = Yellow_person()
bai.speak()  # 白種人說話的方法
hei.speak()  # 黑種人說話的方法
huang.speak()  # 黃種人說話的方法
  1. 強制實現多型

import abc
# 指定metaclass屬性將類設定為抽象類,抽象類本身只是用來約束子類的,不能被例項化
class Person(metaclass=abc.ABCMeta):
    @abc.abstractmethod  # 該裝飾器限制繼承它的子類必須有一個名為speak的方法
    def speak(self):  # 抽象方法中無需實現具體的功能
        pass
class White_person(Person):  # 繼承了Person類的子類內部必須有名為speak的方法,沒有就會報錯
    def speak(self):
        print('白種人說話的方法')
class Black_person(Person):  # 繼承了Person類的子類內部必須有名為speak的方法,沒有就會報錯
    def speak(self):
        print('黑種人說話的方法')
class Yellow_person(Person):  # 繼承了Person類的子類內部必須有名為speak的方法,沒有就會報錯
    def talk(self):
        print('黃種人說話的方法')

bai = White_person()
hei = Black_person()
huang = Yellow_person()
bai.speak()
hei.speak()
huang.speak() 

面向物件之反射

反射的含義

	反射是指程式可以訪問、檢測和修改本身狀態或者行為的一種能力,其實就是通過字串來操作物件的資料和功能
的能力。
  1. 反射的四個方法

hasattr():判斷物件是否含有字串對應的功能或者資料
getattr():根據字串獲取對應的變數名或者函式名
setattr():根據字串給物件設定鍵值對(名稱空間中的名字)
delattr():根據字串刪除物件對應的鍵值對(名稱空間中的名字)
  1. 反射的簡單演示

class Student1:
    school = '復旦大學'
    student_id = 123
    def choose(self):
        pass

obj = Student1()
print(hasattr(obj,'school'))  # 含有就返回True
print(hasattr(obj,'teacher'))  # 不含有就返回False
print(getattr(obj,'school'))  # 復旦大學 含有就返回對應的值
print(hasattr(obj,'teacher'))  # 不含有就返回False
setattr(obj,'student_class','python12')  # 不含有就建立
setattr(obj,'student_id','python12')  # 含有就修改
print(obj.student_class)  # python12
print(obj.student_id)  # python12
delattr(obj,'student_class')
print(hasattr(obj,'student_class'))  # False

這裡是IT小白陸祿緋,歡迎各位大佬的指點!!!