1
面向过程编程和面向对象编程
在介绍面向对象之前,先了解一下什么是面向过程编程,所谓的面向过程编程就是将需要解决的问题分析分解为若干步骤,按照步骤一步一步执行,并完成得到最后结果,更偏向机器思维。
而面向对象更符合人类的思维。面向对象编程,就是把要解决的问题抽离抽象出一系列对象,通过各个对象的行为关系,完成整个过程得到最后结果。也就是说“对象”是程序的基本单元,一个对象包含数据和操作数据的函数,面向对象编程就是一组对象的集合。
2
面向对象
上面只是简单的,笼统的说了一下面向对象。下面将具体的学习面向对象。
面向对象编程,需要提取“对象”,那什么是对象呢?所谓的对象,就是将某些事物归纳为一类,在python中称为class,python中如何定义一个class呢?结构如下:
classClassName(bases):
'class document string'
class_suite
class关键字后面跟着的是一个类的名字,类名在命名时需要大写字母开头。bases位置可以是一个或者多个,用于继承父类的集合。如果没有父类需要继承,就需要继承所有类都需要继承的基类object类。‘class document string’这个位置是类的文档,通常规范的编码是需要写的,但是也可以不写。Class_suite的位置就是类的核心内容包括类的成员,方法,数据属性。以上就是类的结构。
下面具体说明一下,类中的属性和方法。
类中的属性,其实就是定义在类内部的变量。方法,就是定义在类内部的方法,但是这个方法或者函数在定义的时候,形参第一个参数永远是self,为了方便引用对象自身性质。通过一个具体例子真切的感受一下:
classDog(object):
max_age =12#属性
defrun(self):#方法
print('dog is running')
现在对象已经创建出来了我们如何引用它呢?
以上面例子为例,首先需要实例对象。即 dog = Dog()这时候dog就是一个实例对象,这个过程可以理解为将Dog这个类一个笼统类,就具体化了,具体化以后就可以使用类内部的属性和方法了, dog.max_age/dog.run()。虽然实例化了但是dog这个对象,但依然属于Dog这个大类,当然就可以继承和具有Dog的所有属性和方法了。其实这里面涉及面向对象的三个特点:数据的封装,继承和多态。上面例子就体现了继承的特点。
3
内置的类属性
内置属性就是没有还可以使用的一写属性,格式是ClassName.__属性__。也是上面Dog类举例,举例如下:
print(Dog.__name__)#获取类名
print(Dog.__doc__)#获取类的文档字符串,即在类的定义中获取‘class document string’中的内容
print(Dog.__bases__)#所有父类构成的元组
print(Dog.__dict__)#获取属性
print(Dog.__module__)#获取类定义所在的模块
print(Dog.__class__)#对应的类
运行结果如下:
上面这些内置属性了解一下就好。
4
类的初始化
在类的定义中通常需要进行一下初始化,方便在类的实例化的过程中直接调用。说白了就是在类的内部再定义一个方法,即__init__方法(一定这么写),__init__这个方法就是用来初始化的,但是要记住,类内部的方法第一个行参一定是self,具体例子如下:
classDog(object):
def__init__(self,name,age):
self.name = name
self.age = age
定义过程如上面例子。但是如何使用呢?即在实例的化的时候就需要将用的参数给定义好,即dog = Dog(‘aa’,8)。因为实例化过程__init__函数会被调用,所以就需要在实例化的时候将__init__需要的参数给传进去,这样才能完成实例化。这时候调用dog.age和dog.name,得到结果就是8和‘aa’,可以理解为我们直接实例化了一个name是‘aa’,age是8的dog。
5
继承和多态
在之前我们提到过继承的概念,就是在定义某个类的时候可以继承一个或者多个其他的类,这个被继承的类我们称为这个类的父类,这个被继承的类也称为基类。通过继承,子类就具有了父类的属性,这样就实现了代码的重用。需要特殊说明的是当调用方法的时候是先从子类中找,如果子类中没有就会去父类中找,一直往上。
多态有点相对于继承,通过继承,子类获得父类的中的一些属性,但是子类并不是跟父类完全一样,子类可以有属于自己的一些属性,这就体现了多态。通俗点说,就是一个基类可以被多个子类继承,每个子类既继承了基类中的属性,但又具有各自的不同属性,这就是多态。在实际的使用中,比较常见的就是父类的引用指向子类对象。多态使用举例如下:
classAnimal(object):
defrun(self):
print('Animal is running')
classCat(Animal):
defrun(self):
print('Cat is running')
classDog(Animal):
defrun(self):
print('Dog is running')
deffunc(Animal):#这个接口体现多态
Animal.run()
c1 = Cat()
d1 = Dog()
func(c1)
func(d1)
打印出的结果:
Cat is running
Dog is running
在定义的时候只定义了一个Animal,但是调用的时候通过传入不同的子类,分别打印出不同的结果。
6
常用的BIF
1
issubclass(sub,sup):用来判断一个类是否是另一个类的子类。
当sub是sup的子类/子孙类或者自身的时候,返回的为True。大家可以用上面例子试一下:
print(issubclass(Dog,Animal))
打印结果:True。
2
isinstance(obj,Class):判断obj是否是Class类的一个实例。
继续上面例子,举例如下:
print(isinstance(c1,Cat))
打印结果:True。
很明显c1,确实是Cat的一个实例,因为前面我们自己定义的。
3
hasattr(obj,name):检查属性是否存在/getattr(obj,name[,default])访问属性/setattr(obj,name,value):设置属性,如果不存在则新建此属性/delattr(obj,name)删除属性。
举例如下:
classAnimal(object):
has_name =Truematchmatch
age =10
defrun(self):
print('Animal is running')
print(hasattr(Animal,'has_name'))
setattr(Animal,'age',12)
print(getattr(Animal,'age'))
delattr(Animal,'has_name')
print(hasattr(Animal,'has_name'))
打印结果:
True
12
False
4
dir():获得一个对象的所有属性和方法/super():获得相应父类/vars():函数返回对象object的属性和属性值的字典对象。
具体例子大家自己试一下吧。
7
访问限制
在python中有些变量并不能随意访问,有些约定俗成,其中变量名以__开头,称为私有变量,只允许内部访问,外部不能访问。但是以__XXX__这样定义的变量称为特俗变量是可以访问的,以_X这样开头的变量可以访问但是不要随意访问。如果有些变量不能在外部被调用,而我们还想使用怎么办呢?通常的做法是在内部定义一些方法,将这个变量暴露出来。
8
总结
前面说了一大堆,对于没有计算机基础的同学来说还是云里雾里的。再做一下总结。
编程中引入面向对象就是为了改变编码的方式,使编码更符合人类思维,更容易理解。因此抽象出了一些类,类中具有属性和方法。而类就是对象的集合(上面例子中可以理解Animal是一个类,而Cat和Dog就对象),实例化过程就是将对象实例给了一个变量,(可以想象成由抽象的变为具体的)。有了对象和实例化并不能充分发挥面向对象的好处。这时候继承和多态就体现出来了。通过继承,子类可以继承父类的属性和方法,从而节省代码,有时候继承的方法不满意也可以重写父类中的方法。通过多态,我们就可以定义一个接口,就可以根据实际得到各自不同的结果。到目前为止只是介绍了面向对象中一些基础的概念和简单的应用,在实际的开发中面向对象远比这要发杂和更多的知识点。完事开头难,一步一步来。
说明:一般我都会将文章写的尽量简短,带来的问题就是有些问题可能说明的不够透彻,对于基础不好的同学,可能就会理解不够透彻,希望大家在后台留言,如果某个知识点大家反馈的比较多,我会通过视频的方式直观的给大家说明!
转载请注明出处,有任何问题欢迎后台留言。
领取专属 10元无门槛券
私享最新 技术干货