python:面向对象和类

Posted

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了python:面向对象和类相关的知识,希望对你有一定的参考价值。


面向过程和面向对象编程思想:
面向对象--Object Oriented Programming,简称oop,是一种程序设计思想。在说面向对象之前,先说一下什么是编程范式,编程范式你按照什么方式来去编程,去实现一个功能。举个例子,你要做饭,
可以用电磁炉,也可以用煤气灶。不同的编程范式本质上代表对各种类型的任务采取的不同的解决问题的思路,两种最重要的编程范式分别是面向过程编程和面向对象编程。
提到面向对象,就不得不提到另一种编程思想,面向过程;什么是面向过程呢,面向过程的思想是把一个项目、一件事情按照一定的顺序,从头到尾一步一步地做下去,先做什么,后做什么,一直到结束。这
种思想比较好理解,其实这也是一个人做事的方法,我们之前编程的思想也都是使用这种思想。这种编程思想,只要前面有一个步骤变了,那么后面的就也要变,后面维护起来比较麻烦,这样的编程思想,我
们在写一些简单的小程序、只执行一次的脚本时可以使用。而面向对象呢,面向对象的思想是把一个项目、一件事情分成更小的项目,或者说分成一个个更小的部分,每一部分负责什么方面的功能,最后再由
这些部分组合而成为一个整体。这种思想比较适合多人的分工合作,就像一个大的机关,分各个部门,每个部门分别负责某样职能,各个部门可以充分发挥自己的特色,只要符合一定前提就行了。
举个例子:比如刚才说的一个大的机关,要做某一个项目,从面向过程的思想来说,应该是这样分析的,先怎么样,再怎么样,最后怎么样。第一样应该如何完成,第二样应该如何完成等等。等到每一步骤都
完成,项目也就完成了。而面向对象的思想则应该是这样想的,这个项目是由几个部分组成的,我们就做好分工,成立一个部门来做一个部分的功能,另一个部门来做另一个部分。各个部门可以不用理解其他
部门的事,只要完成自己那一部分的事情就OK了。

面向对象的特性:类,对象,实例化
类:class
类,对比现实世界来说就是一个种类,一个模型。
一个类即是对一类拥有相同属性的对象的抽象、蓝图、原型。
在类中定义了这些对象的都具备的属性(variables(data))、共同的方法。
对象:object
对象,也叫实例,也就是指模型造出来的具体的东西。
一个对象即是一个类的实例化后实例,一个类必须经过实例化后方可在程序中调用,一个类可以实例化多个对象,每个对象亦可以有不同的属性,就像人类是指所有人,每个人是指具体的对象,
人与人之前有共性,亦有不同。
实例化:
初始化一个类,造了一个对象。把一个类变成一个具体的对象的过程,叫做实例化。
属性:
比如说汽车的颜色、品牌、排量;即变量
功能:
比如汽车有导航、听歌、跑等的功能;即函数
class BuyCar(object):
#新式类
pass
class BuyCar2:
#经典类
pass
#python3里面经典类和新式类没有任何的区别,写的时候一般用新式类

#创建类
class BuyCar(object): #object是基类
def sale(self): #类里面函数默认加上self,不写会报错
#self代表实例化之后的这个对象,为了节省内存而设计的
print(‘卖车‘)
def insurance(self):
print(‘买保险‘)
def check(self):
print(‘验车‘)
def card(self):
print(‘选牌‘)
def pay(self):
print(‘付款‘)
def done(self):
print(‘完成‘)
#类不能是直接用;能用的是实例或对象

#实例化:
me=BuyCar() #这个过程就是实例化对象,me是实例,也叫对象
#如果是函数名加括号,就是调用函数
#如果是类名加括号,就是实例化对象
me.sale()
me.check()
me.card() #实例化后,对象就可以调用类里面的方法(即函数)

# 构造方法、析构方法:
class Car(object):
wheel=4 #此处的wheel叫类变量,所有的实例都可以使用;直接self.wheel就可以使用
def __init__(self,colors,pls,pzs): #__init__是构造方法
#构造方法在实例化这个类的时候就会执行,其他的方法必须调用才能执行
#如果想在类初始化的时候给它传一些参数,那就要在构造方法里面写参数
self.color=colors
#给实例化的对象添加属性;此处的color pl pz 叫实例变量,区别于类变量
self.pl=pls
self.pz=pzs
def __del__(self):
#析构方法:作用是1.对象被销毁时(del 实例化对象)执行
#2.程序运行完成之后执行,类的生命周期结束时调用析构函数,然后释放内存
print(‘over...‘)
def driver(self):
print(‘汽车的颜色是:‘,self.color)
self.run()
#self在类里面代表实例化的对象,直接点.可以点出来定义的属性和方法
print(‘driver‘)
def run(self):
print(‘run‘)
your_car=Car(‘red‘,‘5.0‘,‘悍马‘) #构造方法里的传参在实例化时直接填参数就可

例子:
import pymysql
class MyDbError(Exception):
def __str__(self):
return ‘数据库连接错误‘
class MyDb(object):
def __init__(self,host,user,passwd,db,port=3306,charset=‘utf8‘):
try:
self.conn=pymysql.connect(
host=host,user=user,passwd=passwd,
db=db,port=port,charset=charset
)
except Exception as e:
raise MyDbError
#主动抛出异常,有raise的话,程序出异常就不会再往下进行
else:
self.cur=self.conn.cursor(cursor=pymysql.cursors.DictCursor)

def select(self,sql):
try:
self.cur.execute(sql)
except Exception as e:
return e
return self.cur.fetchall()
def other(self,sql):
try:
self.cur.execute(sql)
except Exception as e:
return e
self.conn.commit()
return self.cur.rowcount
#如果sql执行成功,返回影响的行数
def __del__(self):
self.cur.close()
self.conn.close() #这个类不用的时候,就执行析构方法,关闭数据库

#私有变量和私有方法:
import xlrd
class ReadCase(object):
__name=‘hahaha‘
#类变量加俩下划线是私有变量;只能在类里面用,出了类就不行了
#比如出了这个类,实例化为r,r.__name是错的,而且也点不出来
def __set(self):
self.money=259999
#函数名前加俩下划线是私有方法
#只能在类里面调用,出了类访问不了
def __init__(self,f_name):
self.fname=f_name
def read_case(self):
book=xlrd.open_workbook(self.fname)
pass
r=ReadCase(‘a.xls‘)


封装:
把一些功能的实现细节不对外暴露,类中对数据的赋值、内部调用对外部用户是透明的,这使类变成了一个胶囊或容器,里面包含着类的数据和方法。

比如说造的一个人,你把他身体内部的什么心肝脾肺肾都封装起来了,其他人都看不到,你直接找这个人。

继承:
一个类可以派生出子类,在这个父类里定义的属性、方法自动被子类继承。比如说你继承了你父亲的姓。
python3中多继承都是广度优先,python2中经典类的多继承是深度优先,新式类的多继承是按照广度优先的。
继承是为了代码的重用
eg1:
class Person(object):
def __init__(self,,name,sex):
self.name=name
self.sex=sex
def cry(self):
print(‘哭‘)
class Man(Person): #括号里填入Person,就是继承了Person的属性和方法
def work(self):
print(‘working...‘)
hn=Man(‘hn‘,‘nv‘) #实例化Man,因为继承了Person,所以实例化时也得传参
hn.name
hn.cry()
#实例化的Man,可以调用Person的方法和属性
eg2:
class Children(Person,Man): #可以继承多个类
pass
hh=Children(‘hh‘,‘nan‘)
hh.work()
hh.cry()
#多继承,Person Man有的方法和属性,Children都有
#多继承,如果被继承的几个类里有名字形同的函数,那继承者继承的方法是括号里排最前的类,这种在python3里叫广度优先
#在python2里,如果是经典类的话,是深度优先;新式类的话,还是广度优先


多态(python不直接支持):
对不同类的对象发出相同的消息将会有不同的行为。比如,你的老板让所有员工在九点钟开始工作, 他只要在九点钟的时候说:“开始工作”即可,而不需要对销售人员说:“开始销售工作”,
对技术人员说:“开始技术工作”, 因为“员工”是一个抽象的事物, 只要是员工就可以开始工作,他知道这一点就行了。至于每个员工,当然会各司其职,做各自的工作。
多态就是抽象化的一种体现,把一系列具体事物的共同点抽象出来, 再通过这个抽象的事物, 与不同的具体事物进行对话。
一种方法,多种实现。
eg1:
class My(object):
def say(self,msg):
print(msg)
def say(self,age,sex):
print(age,sex)
def say(self,addr,phone,money):
print(addr,phone,money)
#java里,多态是这么实现的,通过不同的参数,调用函数
#在python,里函数名不能重复,不能这么写;但可以间接实现多态,见下面eg2
eg2
class Cat(object):
def speak(self):
print(‘喵喵喵‘)
class Dog(object):
def speak(self):
print(‘汪汪汪‘)
c=Cat()
d=Dog()
obj=[c,d]
for i in obj:
i.speak() #通过这种方法间接实现多态;但不经常用

重写父类的构造方法、__str__方法
重写父类的构造方法时,必须要先调用一下父类的构造方法,例子见下面:
class OpDb(object):
def __init__(self,ip,passwd,port,db):
self.ip=ip
self.passwd=passwd
self.port=port
self.db=db
import redis
class MyRedis(OpDb):
def set(self,k,v):
r=redis.Redis(host=self.ip,port=self.port,passwd=self.passwd,)
r.set(k,v)
class MySql(OpDb):
def __init__(self,ip,passwd,port,db,user,charset=‘utf8‘):
# MySql继承父类OpDb,但它俩都有__init__方法,实例化MySql的时候,调用的是MySql自己的__init__方法
OpDb.__init__(self,ip,passwd,port,db)
#想用到父类OpDb的__init__这个方法的话,还得先要调用一下父类的这个方法
#如果此处不调用OpDb的__init__方法,就要写上self.ip=ip self.passwd=passwd等,比较麻烦而且low
#super(OpDb,self).__init__(ip,passwd,port,db)
#super这个句子和上面调用父类OpDb的__init__方法的效果是一模一样的,super这个比较高级一点
self.user=user
self.charset=charset
def __str__(self):
return "这个是执行sql的类"
Hn_Mysql=Mysql(‘192.168.1.1‘,‘123456‘,3306,‘test‘,‘root‘)
print(Hn_Mysql) #打印的结果不是Hn_Mysql的内存地址,而是"这个是执行sql的类",__str__方法就是这个用途

静态方法、类方法:
class Stu(object):
country = ‘china‘ # 类变量
def __init__(self, name):
self.name = name
@staticmethod
def say():
# 静态方法,加了staticmethod装饰器的函数,括号里不用写self了,和类本身没有什么关系了,就相当于在类里面定义了一个方法而已
print(‘xxx‘)
@classmethod
def hello(cls):
# 这个叫类方法,和静态方法不同的是,它可以使用类变量,必须要传一个cls,代表的就是这个类
print(cls.country)
def hi(self):
# 这个是实例方法
print(self.name)
t = Stu(‘name‘)
Stu.hello()
Stu.say()
t.hi()
t.say()
t.hello()
























































































































































































































































以上是关于python:面向对象和类的主要内容,如果未能解决你的问题,请参考以下文章

python 对象和类

Python_016(面向对象之属性和类方法)

python 面向对象和类成员和异常处理

面向对象和类

Python面向对象之静态方法和类方法

Python实用笔记 (22)面向对象编程——实例属性和类属性