# class object
类 具有相同属性和方法的一个整体 对象(实例) 类的一个具体的个体 实例化 就是类-->对象的过程 类在python中 变量表示特征,函数表示技能 面向对象优点:面向对象编程可以使程序的维护和拓展变得简单,且可以大大提高开发效率
类的创建 class 类名: def __init__(name,age,sex): self.name = name ... def chi(self): pass
对象是关于类而实际存在的一个例子 def Person(*args,**kwargs): #函数模拟的类 self = {} def attack(self,dog): dog['life_value'] -= self['aggressivity'] def __init__(name,aggressivity,life_value): self['name'] = name self['aggressivity'] = aggressivity self['life_value'] = life_value self['attack'] = attack __init__(*args,**kwargs) return self egg = Person('egon',78,10) print(egg['name'])
# 面向对象的组合用法 # 软件重用的重要方式除了继承还有组合 # 组合指的是在一个类中以另一个类的对象作为数据属性
一个例子 class Weapon: def zha(self,obj): obj.life_value -= 500 class Person: role = 'human' def __init__(self,name): self.name = name self.weapon = Weapon() #给角色绑定一个武器 sara = Person('sara') sara.weapon.zha() #里面需要传入obj
# 圆环的实现 from math import pi class Circle: #圆 def __init__(self,radius): #半径 self.radius = radius def area(self): #面积 return pi*self.radius**2 def chang(self): #周长 return 2*pi*self.radius c = Circle(10) #实例化一个圆 class Ring: #圆环类 def __init__(self,out_r,in_r): #外径 内径 self.out_c = Circle(out_r) #外圆 self.in_c = Circle(in_r) #内圆 def area(self): #面积 return self.out_c.area() - self.in_c.area() def chang(self): #长度 return self.out_c.chang() + self.in_c.chang() ring = Ring(10,5) #实例化一个圆环 print(ring.chang()) print(ring.area())
用组合的方式建立了类与组合的类之间的关系,它是一种‘有’的关系,比如教授有生日,教授教python课程
class BirthDate: #生日类 def __init__(self,year,month,day): self.year=year self.month=month self.day=day class Couse: #课程类 def __init__(self,name,price,period): self.name=name self.price=price self.period=period class Teacher: #老师类 def __init__(self,name,gender,birth,course): self.name=name self.gender=gender self.birth=birth self.course=course def teach(self): #教 print('teaching') p1=Teacher('chao','male', BirthDate('1995','1','27'), Couse('python','28000','4 months') ) #实例化一个老师对象 print(p1.birth.year,p1.birth.month,p1.birth.day) print(p1.course.name,p1.course.price,p1.course.period)
小贴士:当类之间有显著不同,并且较小的类是较大的类所需要的组件时,用组合比较好
三大特性 继承 父类(基类 超类) 子类(派生类 派生方法/属性) 表达的是两个类之间什么是什么的关系
why 继承? 几个类有重复的属性和方法,就把相同部分抽象出来作为父类,子类去继承父类
父类与子类的关系? 子类关联父类,父类并不关联子类
子类使用父类的方法:
子类有,父类无: 用子类的
父类有,子类无: 用父类的
子类|父类都有: #默认情况下用子类的不用父类的
#既想用父类,又想用子类 : 父类名.方法名(子类obj), super().方法名()
子类父类中都没: 报错 单继承 SubClass1(ParentClass1) 解决代码冗余的问题,子类继承了父类之后,就可以调用父类的方法了,
子类的对象调用某个方法:obj/自己类/父类 多继承 SubClass2(ParentClass1,ParentClass2) #python支持多继承,用逗号分隔开多个继承的类 类名.__bases__ #所有父类 类名.__base__ #从左到右的第一个父类 tips:如果没有指定基类,python的类会默认继承object类,object是所有类的基类,它提供了一些常见方法(__str__)的实现
class A: def hahaha(self): print('A') class B(A): def hahaha(self): super().hahaha() # super(B,self).hahaha() # A.hahaha(self) print('B') a = A() b = B() # print(b.hahaha()) print(super(B,b).hahaha()) #B类的实例b 集成的A调用hahaha() 结果A None(因为函数里面没有return)
抽象类与接口类
# 判断函数和方法 from types import MethodType,FunctionType class A: def func(self): pass a = A() print(isinstance(a.func,MethodType)) # 对象调用的就是方法 //a.func是不是一个方法类型 print(isinstance(A.func,FunctionType) ) # 类调用的func 就是一个函数
# 一个继承的面试题 class Base: def __init__(self): self.func() def func(self): print('in base') class Son(Base): def func(self): print('in son') s = Son() #in son
# 归一化设计 支付宝/微信支付 class Alipay: def __init__(self,name): self.name = name def pay(self,money): print('%s用支付宝花了%s元'%(self.name,money)) class Wechatpay: def __init__(self,name): self.name = name def pay(self,money): print('%s用微信花了%s元'%(self.name,money)) # 归一化设计 def pay_func(person,money): person.pay(money) lex = Alipay('lex') #实例化 nezha = Wechatpay('nezha') #实例化 pay_func(lex,200) pay_func(nezha,200)
from abc import ABCMeta,abstractmethod #(抽象方法) class Payment(metaclass=ABCMeta): #规范类 约束所有的子类必须实现pay的方法 @abstractmethod #下面一行的pay方法是一个必须在子类中实现的方法 def pay(self,money): pass @abstractmethod def back(self): # 退钱 pass class Alipay(Payment): def __init__(self,name): self.name = name def pay(self,money): print('%s用支付宝花了%s元'%(self.name,money)) pass def back(self): # 退钱 pass class Wechatpay(Payment): def __init__(self,name): self.name = name def pay(self,money): print('%s用微信花了%s元'%(self.name,money)) def back(self): # 退钱 pass class Applepay(Payment): def __init__(self,name): self.name = name def pay(self,money): print('%s用apple支付花了%s元'%(self.name,money)) def back(self): # 退钱 pass # 归一化设计 def pay_func(person,money): person.pay(money) lex = Alipay('lex') #实例化 nezha = Wechatpay('nezha') #实例化 hexi = Applepay('hexi') #实例化 pay_func(lex,200) pay_func(nezha,200) pay_func(hexi,122) # 不符合规范类指定的规则,实例化都做不了 # 抽象类不能实例化 # 抽象类主要就是作为基类/父类,来约束子类中必须实现的某些方法 # 特点: # 必须在定义的时候指定metaclass=ABCMeta # 必须在要约束的方法上方加上@abstractmethod方法
java 不支持多继承
# java 不支持多继承 # python 支持多继承 :通过抽象类的多继承来实现复杂的规范 # 动物园 # 天鹅 : 飞 走 游泳 # 老虎 : 走 游泳 # 鹦鹉 : 飞 走 说话 from abc import ABCMeta,abstractmethod class Fly_Animal(metaclass=ABCMeta): @abstractmethod def fly(self): print('爷会飞') class Swim_Animal(metaclass=ABCMeta): @abstractmethod def swim(self): pass class Walk_Animal(metaclass=ABCMeta): @abstractmethod def walk(self): pass class Swan(Fly_Animal,Swim_Animal,Walk_Animal): def fly(self): super().fly() print('飞') def walk(self):print('走') def swim(self):print('游') class Tiger(Walk_Animal,Swim_Animal): def walk(self):print('走') def swim(self):print('游') class Parrot(Fly_Animal,Walk_Animal): def fly(self):print('飞') def walk(self):print('走') def talk(self):print('说') # 不同动物的相同行为是不能混为一谈 # 不同动物的相同行为的方法名字是必须一样 # python # 抽象类 : 抽象类中的方法可以写一些具体的py代码(规范) # 单继承 # 多继承 # java # 不支持多继承,新的概念 接口 Interface # 和抽象类几乎一模一样的功能 : # 只定义一个接口名字(基类名),内部定义子类必须实现的方法 # 接口支持多继承 # 接口内部的所有方法都不能写具体的代码,只能用pass代替 # 抽象类 : # 单继承的形容,并且在单继承中可以在方法中写python代码 # 接口类 : 更接近java中的接口的概念 # python中由于有了抽象类的多继承,不需要接口的概念了 # 一个基类写出来被子类多继承了 : 接口类 # 并且在方法中只写pass(你可以选择性的满足)
super遵循mro算法
封装: 隐藏对象的属性和实现细节,仅对外提供公共访问方式
优点:
将变化隔离
便于使用
提高复用性
提高安全性
封装原则
将不需要对外提供的内容都隐藏起来
把属性都隐藏,提供公共方法对其访问
私有变量和私有方法 __name
一个静态属性property本质就是实现了get,set,delete三种方法,方法调用的时候不再加()
__foo__: 定义的是特殊方法,一般是系统定义名字 ,类似 __init__() 之类的。
_foo: 以单下划线开头的表示的是 protected 类型的变量,即保护类型只能允许其本身与子类进行访问,不能用于 from module import *
__foo: 双下划线的表示的是私有类型(private)的变量, 只能是允许这个类本身进行访问了
class A: __role = 'CHINA' #私有属性 @classmethod #类方法 def show_role(cls): print(cls.__role) @staticmethod #静态方法 def get_role(): return A.__role @property #特性 def role(self): return self.__role a = A() print(a.role) print(a.get_role()) a.show_role()
面向对象的软件开发 OOA 面向对象分析 object oriented analysis OOD 面向对象设计 object oriented design OOP 面向对象编程 object oriented programming OOT 面向对象测试 object oriented test OOSM 面向对象维护 object oriendted soft maintenance 面向对象常用术语: 抽象/实现 接口/封装 真正的封装是,经过深入的思考,做出良好的抽象,给出“完整且最小”的接口,并使得内部细节可以对外透明
合成
派生/继承/继承结构
泛化/特化
多态/多态性
反射/自省