1. 程式人生 > >Python隨心記--函式之面向物件

Python隨心記--函式之面向物件

函式之面向物件
def dog(name,type):
    def jiao(dog):
        ret = '一隻%s再叫,哈哈哈' % dog['name']
        return ret
    def chi(dog):
        ret = '一隻%s在吃飯,吃吃吃' % dog['type']
        return ret
    def init(name,type):
        dog = {
            'name':name,
            'type':type,
            'jiao':jiao,
            
'chi':chi, } return dog return init(name,type) d1 = dog('小白兔','哈士奇') d2 = dog('小黑兔','阿拉斯加') print(d1['jiao'](d1)) print(d1['chi'](d1)) print(d1['jiao'](d2)) print(d1['chi'](d2))
#面向物件:
類:
動作跟特徵的結合(共同的特徵,共同的動作)
把一類事物的相同的特徵和動作整合到一起
是一個抽象的概念
物件:就是居於類而建立的一個具體的事物
#用面嚮物件語言寫程式和一個程式的設計是面向物件程式設計

#新式類(python2中)
class School(object):
    def __init__(self,name,type):
        self.name = name
        self.type = type
    def bark(self):
        return '%s在招生' %self.name

d = School('清華','公立')   #例項化物件
print(d.bark())

 

#經典類   (__init__裡面不能return值)
class School:   #宣告一個類
    def
__init__(self,name,type): self.name = name self.type = type def bark(self): return '%s在招生' %self.name d = School('清華','公立') #例項化物件 print(d.bark())

 

class Chinese:
    '這是一箇中國類'
    nationality = '中國'   #屬性
    ancestralhome = '廣東'   #屬性
    def __init__(self,name,age,gender):
        self.name = name
        self.age = age
        self.gender = gender
    def common(self):
        return '%s人不吃辣' %self.name
    def commons(self):
        return '%s人喜歡吃辣' %self
print(Chinese.__name__)   #列印類名
print(Chinese.__doc__)   #列印文件
print(Chinese.__base__)
print(Chinese.__bases__)
print(Chinese.__module__)   #模組
print(Chinese.__class__)

chainese = Chinese()
print(Chinese.nationality)   #訪問屬性
print(Chinese.ancestralhome)   #訪問屬性
print(Chinese.common(chainese))   #訪問方法
print(dir(Chinese))
print(Chinese.__dict__)   #檢視類的屬性字典
print(Chinese.__dict__['nationality'])   #列印類的屬性
print(Chinese.__dict__['ancestralhome'])   #列印類的屬性
print(Chinese.__dict__['commons']())   #執行類的方法

chainese = Chinese('廣東','13','中國')
print(chainese.__dict__)
print(chainese.common())

 

class Chinese:
    '這是一箇中國類'
    nationality = '中國'   #屬性
    ancestralhome = '廣東'   #屬性
    def __init__(self,name,age,gender):
        self.name = name
        self.age = age
        self.gender = gender
    def common(self):
        return '%s人不吃辣' %self.name
    def eatfood(self,food):
        return '%s人喜歡喝%s' %(self.name,food)

chainese = Chinese('廣東','13','中國')

print(chainese.common())
print(chainese.eatfood('早茶'))

Chinese.ancestralhome = '深圳'   #修改屬性
chainese.addr = '廣州'   #增加屬性
del Chinese.ancestralhome   #刪除屬性

def eat_food(self,food):
    return '%s人喜歡喝%s' % (self.name, food)

Chinese.eat = eat_food   #增加方法 把eat_food方法增加到Chinese類中
Chinese.common = eat_food   #修改 把common方法修改為eat_food
# print(chainese.__dict__)
print(chainese.eat(''))

 

county = '北京'
class Chinese:
    '這是一箇中國類'
    nationality = '中國'   #屬性
    ancestralhome = '廣東'   #屬性
    def __init__(self,name,age,gender):
        #print(county)   #能列印北京,這裡跟普通變數沒什麼差別,如果用self.county就會報錯
        self.name = name
        self.age = age
        self.gender = gender
    def common(self):
        return '%s人不吃辣' %self.name
    def eatfood(self,food):
        return '%s人喜歡喝%s' %(self.name,food)

chainese = Chinese('廣東','13','中國')

 

面向物件之靜態屬性

class Room:
    tag = 1   #靜態屬性
    def __init__(self,name,length,width,hiegh):
        self.Name = name
        self.Length = length
        self.Width = width
        self.Hiegh = hiegh
    @property   #加上裝飾器
    def cal_area(self):
        return self.Width * self.Length
    def test(self):
        print('from test',self.Name)
    def tall_info(self):
        print('--->',self.tag)

    @classmethod  # 加上只會tall_info就會變成專門給類使用的方法
    def tall_info1(cls):
        print(cls)
        print('--->', cls.tag)
        print('--->', Room.tag)

    @classmethod  # 加上只會tall_info就會變成專門給類使用的方法
    def tall_info2(cls,x):
        print(cls)
        print('--->', cls.tag, x)
room = Room('臥室',100,100,100)
print(room.cal_area())   #加上裝飾器@property之前呼叫
print(room.cal_area)   #加上裝飾器@property之後呼叫

print(Room.tag)   #呼叫屬性
Room.test(room)
Room.tall_info(room)   加上裝飾器@classmethod之前呼叫

Room.tall_info1()   #加上裝飾器@classmethod之後呼叫
Room.tall_info2(10)   #加上裝飾器@classmethod之後呼叫
 
#靜態方法
class Room:
    tag = 1   #靜態屬性
    def __init__(self,name,length,width,hiegh):
        self.Name = name
        self.Length = length
        self.Width = width
        self.Hiegh = hiegh
    @property   #加上裝飾器
    def cal_area(self):
        return self.Width * self.Length
    def test(self):
        print('from test',self.Name)
    def tall_info(self):
        print('--->',self.tag)

    @classmethod  # 加上只會tall_info就會變成專門給類使用的方法
    def tall_info1(cls):
        print(cls)
        print('--->', cls.tag)
        print('--->', Room.tag)

    @classmethod  # 加上只會tall_info就會變成專門給類使用的方法
    def tall_info2(cls,x):
        print(cls)
        print('--->', cls.tag, x)
    @staticmethod   #類的工具包 不能呼叫類變數和例項變數
    def wash_boyd():   #可以傳引數也可以不傳引數
        print('正在洗澡')
room = Room('臥室',100,100,100)

Room.wash_boyd()
room.wash_boyd()
 
組合
class Hand:
    pass
class Foot:
    pass
class Head:
    pass
class Trunk:
    pass
class Person:
    def __init__(self,id_num,name):
        self.id_num = id_num
        self.name = name
        self.hand = Hand()
        self.food = Foot()
        self.trunk = Trunk()
        self.head = Head()
    
 
組合(查詢學校資訊)
#學校類
class School:
    def __init__(self,name,addr):
        self.name = name
        self.addr = addr
#課程類
class Course:
    def __init__(self,name,price,perioc,school):
        self.name = name
        self.price = price
        self.perioc = perioc
        self.school = school

schoolo = School('老男孩','北京')
schoolt = School('傳  智','天津')
schoolh = School('泰  牛','上海')


# print(c1.__dict__)

msg = '''
    1 老男孩北京校區
    2 老男孩天津校區
    3 老男孩上海校區
'''
while True:
    print(msg)
    menu = {
        '1' : schoolo,
        '2' : schoolt,
        '3' : schoolh,
    }
    choice = input('請選擇您想要了解的校區序號>>>:')

    course = Course('liunx', '10000', '6', menu[choice])  # 把學校類傳給課程類
    print('課程屬於【%s】,地址在【%s】' %(course.school.name,course.school.addr))  # 拿到oldboy

 

#繼承、多型、封裝

繼承
 #面向物件之繼承
class ParentClass:
    money = 100
    def __init__(self,name):
        self.name = name
    def hit_son(self):
        return '%s 正在執行' %self.name
class ParentClasss:
    pass
class SubClass(ParentClass):   #單繼承
    pass
class SubClasss(ParentClass,ParentClasss):   #多繼承
    pass

sub = SubClass('函式')
# print(sub.money)
print('子類呼叫父類的hit_son函式',sub.hit_son()) 
 

介面繼承:

  子類必須實現父類的所有方法

 

import abc   #介面模組
class AllFile(metaclass=abc.ABCMeta):
    @abc.abstractmethod
    def read(self):
        pass
    @abc.abstractmethod
    def write(self):
        pass
class Disk(AllFile):
    def read(self):
        print('Disk rand')
    def write(self):
        print('Disk write')
class Cdrom(AllFile):
    def read(self):
        print('Cdrom rand')
    def write(self):
        print('Cdrom write')

class Mem(AllFile):
    def read(self):
        print('Mem rand')
    def write(self):
        print('Mem write')

 

#介面繼承順序之mro線性(python3)
class D:
    pass
class E:
    pass
class F(D,E):
    pass
print(F.__mro__)
 
#在子類中呼叫父類的方法
class Vehicle:
    Country = 'China'
    def __init__(self,name,speed,load,power):
        self.name = name
        self.speed = speed
        self.load = load
        self.power = power

    def run(self):
        return '【父類】開動啦............'


class Subway(Vehicle):
    def __init__(self,name,speed,load,power):
        super().__init__(name,speed,load,power)
        # super(Subway,self).__init__(name,speed,load,power)
        # Vehicle.__init__(self,name,speed,load,power)
    def show_info(self):
        return self.name,self.speed
    def run(self):
        super().run()
        # Vehicle.run(self)
        return '%s線開動了' %(self.name),super().run()
lin13 = Subway('深圳13號線','10km/h',1000,'')

print(lin13.show_info())

print(lin13.run())

 

例項

import uuid
import pickle
import hashlib
import time
def creat_md5():
    m = hashlib.md5()
    m.update(str(time.time()).encode('utf8'))
    return m.hexdigest()
# id = creat_md5()
class Base:
    def save(self):   #把例項物件永久化儲存(檔案方式)
        with open('school.db','wb') as f:
            pickle.dump(self,f)
class School(Base):
    def __init__(self,name,addr):
        self.id = creat_md5()
        self.name = name
        self.addr = addr
#課程類
class Course(Base):
    def __init__(self,name,price,perioc,school):
        self.id = creat_md5()
        self.name = name
        self.price = price
        self.perioc = perioc
        self.school = school

school = School('老男孩','沙河')
school.save()

school_obj = pickle.load(open('school.db','rb'))   #讀出儲存的物件
print(school_obj)

 

#面向物件之多型
 
 
 
class H2o:
    def __init__(self,name,temperature):
         self.name = name
         self.temperature = temperature
    def turn_ice(self):
        if self.temperature < 0:
            return '【%s】溫度太低結冰了' %self.name
        elif self.temperature > 100:
            return '【%s】溫度太高變成蒸汽了' % self.name
        else:
            return '【%s】液化成水了' % self.name

class Water(H2o):
    pass

class Ice(H2o):
    pass

class Steem(H2o):
    pass

water = Water('',10)
ice = Ice('',-20)
steem = Steem('蒸汽',123)

print(water.turn_ice())
print(ice.turn_ice())
print(steem.turn_ice())
 
#面向物件之封裝:
腦子不好使的先別封,沒想全面的別封,不然最後你會瘋
1 改變 2 擴充套件
明確內外可否呼叫,內部能用外部不能用
多型就是類的這兩層意義的一個具體的實現機制,即呼叫不同的類例項化的物件下的相同方法,實現的過程不一樣,python中的標準型別就是多型概念的一個很好的示範
真正意義的封裝不是停留在封裝的層面上
 
 
 
class People:
    stars = 'earth'
    _star = 'earth'   #被隱藏的屬性 類之外不應該被呼叫,能呼叫
    __star = 'earth'   #被隱藏的屬性(類似私有的) 類之外不能被呼叫 如非要呼叫可如: peoplo._People__star 原因是pythonn會重新命名
    __width = 23
    __lenfth = 24
    def __init__(self,id,name,age,salary):
        self.id = id
        self.name = name
        self.age = age
        self.salary = salary
    def _get_id(self):
        print('這是我的私有方法,我找到的id是[%s]' %self.id)
    
    def teststar():
        print(self.__star#外部人可呼叫該函式求面積
    def tell_area():
        return self.__width * self.__lenfth
peoplo = People('232333233','linm','13',1000000)
peoplo._get_id()
print(peoplo.__star)
peoplo.teststar()