目录
python是面向对象的一门语言。
面向对象技术简介:
- 类(Class): 用来描述具有相同的属性和方法的对象的集合。它定义了该集合中每个对象所共有的属性和方法。对象是类的实例。
class ClassName: '类的帮助信息' #类文档字符串 class_suite #类体
- 类变量:类变量在整个实例化的对象中是公用的。类变量定义在类中且在函数体之外。类变量通常不作为实例变量使用。类变量:定义在类里面,通过类名或对象名引用,如果是通过对象名引用,会先找有没有这个同名的实例变量,如果没有,引用到的才是类变量,类变量的更新,只能通过类名,形如 类名.a = 55 ,不要指望通过实例引用类变量来更新类变量
- 局部变量:定义在方法中的变量,只作用于当前实例的类
- 实例变量:在类的声明中,属性是用变量来表示的。这种变量就称为实例变量,是在类声明的内部但是在类的其他成员方法之外声明的。定义在方法里面的变量,一般在__init__里面,只能通过对象名引用,实例变量的增加、更新形式,形如self.a = 55
- 数据成员:类变量或者实例变量, 用于处理类及其实例对象的相关的数据。
- 方法重写:如果从父类继承的方法不能满足子类的需求,可以对其进行改写,这个过程叫方法的覆盖(override),也称为方法的重写。
- 继承:即一个派生类(derived class)继承基类(base class)的字段和方法。继承也允许把一个派生类的对象作为一个基类对象对待。例如,有这样一个设计:一个Dog类型的对象派生自Animal类,这是模拟"是一个(is-a)"关系(例图,Dog是一个Animal)。
- 实例化:创建一个类的实例,类的具体对象。
- 方法:类中定义的函数。
- 对象:通过类定义的数据结构实例。对象包括两个数据成员(类变量和实例变量)和方法。
一、python中类的定义与实例的创建
在Python中,类通过 class 关键字定义,类名通用习惯为首字母大写,Python3中类基本都会继承于object类,语法格式如下,我们创建一个Circle圆类:(我们定义的类都会继承于object类,当然也可以不继承object类;两者区别不大,但没有继承于object类使用多继承时可能会出现问题。)
class Circle(object): # 创建Circle类,Circle为类名
pass # 此处可添加属性和方法
创建实例使用 类名+(),类似函数调用的形式创建:
circle1= Circle()
circle2= Circle()
二、python中的实例属性和类属性
类的属性是用来表明这个类是什么的。类的属性分为实例属性与类属性两种。
类属性是每个实例的共有属性。实例属性用于区分不同的实例;
实例属性访问优先级比类属性高
1.实例属性
circle1.r = 1 # r为实例属性
circle2.R= 2
print(circle1.r) # 使用 实例名.属性名 可以访问我们的属性
print(circle2.R)
如上 circle1.r、circle2.R 大小写有区分,两个实例的属性名称不统一不利于后面的访问和使用,而且每次在创建圆后我们要再为实例添加属性会比较麻烦,所以我们可以在创建实例时给类初始属性。
在定义 Circle 类时,可以为 Circle 类添加一个特殊的 __init__() 方法,当创建实例时,__init__() 方法被自动调用为创建的实例增加实例属性。
我们在此为每个实例都统一加上我们需要的属性(用法类似java的构造方法):
class Circle(object): # 创建Circle类
def __init__(self, r): # 初始化一个属性r(不要忘记self参数,他是类下面所有方法必须的参数)
self.r = r # 表示给我们将要创建的实例赋予属性r赋值
注意:__init__() 方法的第一个参数必须是 self,这是类方法区别于普通函数的特别之处(self代表类的实例,可以用别的名字,但建议使用约定成俗的self),后续参数则可以自由指定,和定义函数没有任何区别。
相应,创建实例时就必须要提供除 self 以外的参数:
circle1 = Circle(1) # 创建实例时直接给定实例属性,self不算在内
circle2 = Circle(2)
print(circle1.r) # 实例名.属性名 访问属性
print(circle2.r) # 我们调用实例属性的名称就统一了
2.类属性
圆周率π为圆的共有属性,我们可以在Circle类添加pi这个类属性,如下
class Circle(object):
pi = 3.14 # 类属性
def __init__(self, r):
self.r = r
circle1 = Circle(1)
circle2 = Circle(2)
3.self用法详解
由于类起到模板的作用,因此,可以在创建实例的时候,把我们认为必须绑定的属性强制填写进去。这里就用到Python当中的一个内置方法__init__
方法
例如在Student类时,把name、score等属性绑上去:
class Student(object):
def __init__(self, name, score):
self.name = name
self.score = score
注意:(1)__init__
方法的第一参数永远是self
,表示创建的类实例本身,因此,在__init__
方法内部,就可以把各种属性绑定到self,因为self就指向创建的实例本身。
(2)有了__init__
方法,在创建实例的时候,就不能传入空的参数了,必须传入与__init__
方法匹配的参数,但self不需要传,Python解释器会自己把实例变量传进去:
另外,这里self
就是指类本身,self.name
就是Student
类的属性变量,是Student
类所有。而name
是外部传来的参数,不是Student
类所自带的。
故,self.name = name
的意思就是把外部传来的参数name
的值赋值给Student类自己的属性变量self.name
。
二、类的继承和方法重写
继承是指将现有类的属性和行为,经过修改或重写(Override)之后,就可产生出拥有新功能的类,这样可以大幅提升程序代码的可重用性。
继承分为单继承和多继承
1.单继承
所谓单继承(Single Inheritance),即派生类直接继承单独一个基类的成员数据与成员函数。在 Python 中使用继承机制定义子类的语法格式如下。
class ChildClass(ParentClass):
代码块
class MobilePhone: #基类
def touch(self):
print('我能提供屏幕触控操作的功能')
class HTC(MobilePhone): #派生类
pass
#产生子类对象
u11 = HTC()
u11.touch() #调用继承自 MobilePhone 基类的touch()方法
多继承
多继承声明语句的语法如下。
class ChildClass(ParentClass1, ParentClass2,…):
程序代码块
class Animal: #祖父类
def feature1(self):
print('大多数动物能自发且独立地移动')
class Human(Animal): #父类一
def feature2(self):
print('人类是一种有思考能力与情感的高级动物')
class Fish(Animal): #父类二
def feature3(self):
print('水生脊椎动物的总称')
class Mermaid(Human, Fish): #子类同时继承两种类
def feature4(self):
print('又称人鱼,传说中的生物,同时具备人及鱼的部分特性')
#产生子类实体
alice = Mermaid()
alice.feature1()
alice.feature2()
alice.feature3()
alice.feature4()
继承中的重写:当我们从基类继承所有的成员后,在原先的基类内可能有某些成员函数不符合程序的需要。
事实上,不一定所有继承的成员都必须照单全收,用户可以在派生类中以相同名称、相同参数以及相同的返回值的方法来取代基类的方法。利用这种方式来建立派生类成员函数的动作称为重写。
简单来说,重写就是重新改写所继承的父类的方法,但不会影响到父类中原来的方法。以下程序示范了如何在子类中重写父类的方法。
#在子类中重写父类的方法
class Normal(): #父类
def subsidy(self, income):
self.money = income
if self.money >= 500000:
print('小康家庭补助金额:', end = ' ')
return 5000
class Poor(Normal): #子类
def subsidy(self, income): #重写subsidy方法
self.money = income
if self.money < 300000:
print('中低收入家庭补助金额:', end = ' ')
return 10000
student1 = Normal()#建立父类对象
print(student1.subsidy(780000),'元')
student2 = Poor()#建立子类对象
print(student2.subsidy(250000),'元')
三、多态
多态是指一类事物有
多种形态,比如动物类,可以有猫,狗,猪等等。(一个抽象类有多个子类,因而多态的概念依赖于继承),所以类的多态特性要满足以下 2 个前提条件:
- 继承:多态一定是发生在子类和父类之间;
- 重写:子类重写了父类的方法。
class Animal(metaclass=abc.ABCMeta): #同一类事物:动物 def talk(self): pass class Cat(Animal): #动物的形态之一:猫 #继承自animal类 def talk(self): #重写父类的方法 print('say miaomiao') class Dog(Animal): #动物的形态之二:狗 def talk(self): print('say wangwang') class Pig(Animal): #动物的形态之三:猪 def talk(self): print('say aoao') c = Cat() #实例化子类对象 d = Dog() p = Pig() def func(obj): obj.talk() func(c) func(d) func(p) #即一个接口多种实现