python是一门面向对象的编程语言_Python面向对象(一)

Python也是一门面向对象的编程语言。下面就让我们走进Python的面向对象编程世界。但是在正式进行python的面向对象编程时,得先了解一些Python中类的知识。

类是Python实现支持继承的新种类的对象的部件,也是Python面向对象程序设计(OOP)的主要工具。

PYthon中类的建立使用了一条新的语句:class语句。

1、面向对象有三大特点:

封装

继承

多态

2、什么叫类?

类(Class):用来描述具有相同的属性和方法的对象的集合。它定义了该集合中每个对象所共有的属性和方法。对象是类的实例。概括的讲,类就是一些函数的包,这些函数大量使用并处理内置对象类型。类的设计也是为了创建和管理对象,并且支持继承,这是一种代码定制和复用的机制。

从具体的程序设计观点来看,类是Python的程序组成单元,就像我们之前说的函数和模块一样,类是封装逻辑和数据的另一种方式。类由三个重要的独到之处,使其在建立新对象时更有用。

多重实例

类基本上就是产生对象的工厂。每次调用一个类,就会产生一个独立命名空间的新对象。每个由类产生的对象都能读取类的属性,并获得自己的命名空间储存数据,这些对象对于每个对象来说都不同。

通过继承进行定制

类也支持OOP的继承。我们可以在类的外部重新定义其属性或者增加没有的方法从而扩充这个类。更通用的是,类可以建立命名空间的层次结构,而这种层次结构可以定义该结构中类创建的对象所使用的变量名。所有从类产生的实例都会继承该类的所有属性和方法。

运算符重载

通过提供特定的协议方法,类可以定义对象来响应在内置类型上的几种运算。例如,通过类创建的对象可以进行切片、级联和索引等运算。Python提供了一些可以由类使用的钩子,从而能够中断并实现任何的内置类型运算。

3、创建类

使用class语句来创建一个新类,class之后为类的名称,括号中为基类(可以有多个基类)并且也是以冒号结尾。

class ClassName(BaseClass, ...) :

'optional class documentation string' #类文档字符串

class_suite #类体

class_suite由类成员,方法,数据属性组成。

类的帮助信息可以通过ClassName.__doc__查看。

类定义实例:

#!/usr/bin/python

#coding=utf-8

class Employee (object):

#所有员工基类

empCount = 0

def __init__(self, name, salary) :

#类的构造函数

self.name = name

self.salary = salary

Employee.empCount += 1

def displayCount(self) :

#类方法

print "total employee ",Employee.empCount

def displayEmployee(self) :

print "name :",self.name , ", salary :", self.salary

说明:

empCount变量是一个类变量(也叫静态变量),它的值将在这个类的所有实例之间共享。你可以在内部类或外部类使用Employee.empCount访问。

第一个中方法init()是一种特殊方法,被用做类的构造函数或初始化方法,只要创建类的实例时,就会调用这个方法。如果没显示定义这个方法,默认会给一个空的方法。

类方法中参数中的self,代表实例本身,相当于java中的this指针。并且类中所有的方法中都必须有self,并且写在第一个参数位置。

所有类都是继承基类object。

4、创建实例对象

要创建一个类的实例,可以使用类的名称,并通过__init__方法接受参数。

创建一个类的具体对象。每次从类产生实例时,Python都会自动调用名为__init__的方法,也叫类的构造方法,进行数据初始化。新实例会如往常那样传入__init__的self参数。该方法也会在类中被继承。

如给上面的类创建实例:

emp1 = Employee("joy", 10000)

emp2 = Employee("sr", 10000)

如果所定义的类中没有要初始化的参数时,创建实例时,就不需要传入参数。

5、类变量

Python中类变量也叫类的静态成员变量,类变量在整个实例化的对象中是公用的。类变量定义在类中且在函数体外。类变量通常不作为实例变量使用,它的值在这个类的所有实例之间共享。

类变量紧接在类名后面定义,相当于java和c++的static变量

实例变量在__init__里定义,相当于java和c++的普通变量

class Parent(object): # define parent class

parentAttr = 100

def __init__(self):

print "Calling parent constructor"

parentAttr变量就是一个类变量。

6、实例变量

实例变量在__init__里定义,相当于java和c++的普通变量,只作用于当前类的实例。实例变量前面需要加上self关键字。如:

class Person(object):

id = 12 #类静态成员在这儿定义,注意缩进

def __init__(self,name):

self.name = name #类的实例变量

self.__inName = 'ads' #类的实例变量

而在类的实例方法中定义的变量,叫局部变量。

7、类方法和静态方法

类方法和静态方法很想,在调用时,都不需要产生类的实例去调,而是可以直接使用类的名字去调。

但是它们也是有区别的:类方法传参时需要把类本身的实例(cls,指向该类本身)传进入,而静态方法则不需要传任何实例,只有普通参数。

class Person(object):

id = 12 #类静态成员在这儿定义,注意缩进

def __init__(self,name):

self.name = name

self.__inName = 'ads'

@classmethod #类方法定义,用注解方式说明

def up( cls,a ): #这儿是cls,不是self

print cls,cls.__name__

return a+1

@staticmethod #类静态方法定义,用注解方式说明

def down( b): #静态方法不需要self,cls变量

id = 13

return b-1

调用:

print Person.up(20)

print Person.down(15)

8、方法重载

有时候,我们可能需要在同一个类中定义几个功能类似但参数不同的方法。

方法的重载(overloading)是允许在一个类的定义中,多个方法使用相同的方法名。

如果你学过C++、JAVA或者是其他面向对象编程语言,你会发现Python中的重载与其他面向对象编程语言在使用上是有区别,其实可以这么说Python在形式上是不支持重载。下面先以JAVA为例,讲解一下方法重载。

重载是指在同一类中一个方法名被用来定义多个方法。

方法的重载是面向对象编程语言多态性的一种形式,它实现了java的编译时多态,即由编译器在编译时刻确定具体调用哪个被重载的方法。函数重载大大提高了代码重用率和程序员开发效率。

重载方法的名称是不同的,但在方法的声明中一定要有彼此不相同的成份,以使编译器能够区分这些方法。因此JAVA中规定重载的方法必须遵循下列原则:

方法的参数表必须不同,包括参数的类型或个数,以此区分不同方法体;

方法的返回类型、修饰符可以相同,也可以不同。

public void println()

public void println(char x)

public void println(char x, int x)

(1).Python方法重载

而对于Python来说,虽然它形式上不支持函数重载。但Python也是一门面向对象语言,自然也不会丢弃函数重载这特性。Python中实现函数重载的方法非常特别。首先,Python本身是动态语言,方法的参数是没有类型的,当调用传值的时候才能确定参数的类型,所以想通过参数类型的不同来实现函数重载是不可行了。那到底怎么实现Python的重载呢?

参数类型行不通了,那我们考虑通过参数数量来试试。Python中针对函数参数个数有一个很好使的功能就是缺省参数。

利用重载机制可以进行如下定义:

def println(str1, time = 1) :

print str1 * time

通过设置缺省参数,就可以实现Python中的函数重载。

(2).Python运算符重载(重写)

在Python中,运算符重载的方式很简单,每个类都会有默认内置一些运算符方法,只要重写这个方法,就可以实现针对该运算符的重载。例如下面是重载加法操作:

class Vector(object) :

def __init__(self, a, b) :

self.a = a

self.b = b

def __str__(self):

return 'Vector (%d, %d)' % (self.a, self.b)

def __add__(self,other) :

return Vector(self.a + other.a, self.b + other.b)

x = Vector(3,7)

y = Vector(1, -10)

print x + y

执行结果:

Vector (4, -3)

上面的实例重写了类的加法操作,你也可以重写其他的方法。

9、方法重写

在类层次结构中,当子类的成员变量与父类的成员变量同名时,子类的成员变量会隐藏父类的成员变量;当子类的方法与父类具有相同的名字、参数列表、返回值类型时,子类的方法重写(overriding)了父类的方法,在父类定义的方法就被隐藏。“隐藏”的含义是,通过子类对象调用子类中与父类同名的变量和方法时,操作的是这些变量和方法是在子类中的定义。子类通过成员变量的隐藏和方法的重写可以把父类的状态和行为改成为自身的状态和行为。

重写是指子类重写父类的成员方法。子类可以改成父类方法所实现的功能,但子类中重写的方法必须与父类中对应的方法具有相同的返回值、方法名和参数列表。也就是说要实现重写,就必须存在继承。

方法重写必须遵守的原则:

子类中重写方法的返回值类型必须与父类中被重写方法的返回值类型相同。

子类中重写方法的访问权限不能缩小。

子类中重写方法不能抛出新的异常。

方法重写是现实对象运行时多态的基础。

形状类:

class Shape(object):

def __init__(self,x):

self.x = x

self.rx = 10

def area(self,x):

pass

圆类(继承形状类):

class Circle(Shape):

def __init__(self,x):

#super(Circle,self).__init__(x)

#Shape.__init__(self,x)

pass

def area(self,x):

print 'in circle'

return 3.14 * x ** 2

圆类继承了形状类,并且重写了父类的构造方法和求面积的方法。并且在子类重写父类构造方法时,以父类方法作为一个基础,子类中只是对其做一个扩展,这个时候就会要调用父类的构造方法时,有三种方法:

方法一:(比较灵活)

super(Circle,self).__init__(x) 方法二: Shape.__init__(self,x) 方法三: 子类不定义自己的构造方法时,默认就会调用父类的构造方法。

注意:

super只能用于构造方法中。

如果你的父类不能满足你的需求,你就可以在子类中重写父类的方法,常见重写的父类的方法有:

0818b9ca8b590ca3270a3433284dd417.png

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值