Python面向对象

类与面向对象编程

面向对象编程——Object Oriented Programming,简称OOP,是一种程序设计思想。OOP把对象作为程序的基本单元,一个对象包含了数据和操作数据的函数。

面向过程的程序设计把计算机程序视为一系列的命令集合,即一组函数的顺序执行。为了简化程序设计,面向过程把函数继续切分为子函数,即把大块函数通过切割成小块函数来降低系统的复杂度。

而面向对象的程序设计把计算机程序视为一组对象的集合,而每个对象都可以接收其他对象发过来的消息,并处理这些消息,计算机程序的执行就是一系列消息在各个对象之间传递。

在Python中,所有数据类型都可以视为对象,当然也可以自定义对象。自定义的对象数据类型就是面向对象中的类(Class)的概念。

面向对象思想的优点

  1. 可重用性
    编写可重用模块,比如类
  2. 可扩展性
    要求应用软件能够很方便、很容易的进行扩充和修改
  3. 可管理性
    采用封装了数据和操作的类作为构建系统的部件,使项目组织更加方便合理

抽象数据类型与类

抽象数据类型概念十分简单,抽象数据类型是由一个由对象及对象上操作组成的集合,对象和操作被捆绑成一个整体,可以从程序的一部分传递到另一部分。这个过程中不仅可以使用对象的数据属性,还可以使用对象上的操作。

类的基本思想是数据抽象封装,数据抽象是一种依赖于接口和实现的分离编程技术。类的接口包含用户所能执行的操作,类的实现则包括类的数据成员、负责接口实现的函数以及定义类的各种私有函数。封装实现了类接口和实现的分离,封装后的类隐藏了实现细节,类用户只能访问接口而无法访问实现部分————-《c++ Primer》

继承

在OOP程序设计中,当我们定义一个class的时候,可以从某个现有的class继承,新的class称为子类(Subclass),而被继承的class称为基类、父类或超类(Base class、Super class)

Exp1

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
class IntSet:
"""实现一个整数集合"""

def __init__(self):
"""创建一个空的整数集合"""
self.__vals = []

def insert(self, e):
if e not in self.__vals:
self.__vals.append(e)

def member(self, e):
return e in self.__vals

def remove(self, e):
try:
self.__vals.remove(e)
except:
raise ValueError(str(e) + 'not found')

def getMembers(self):
return self.__vals[:]

def __str__(self):
self.__vals.sort()
result = ''
for e in self.__vals:
result = result + str(e) + ','
return '{'+ result[:-1] + '}'

Exp2

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
import  datetime

class Person:

def __init__(self, name):
self.name = name
try:
lastBlank = name.rindex(' ')
self.lastName = name[lastBlank+1:]
except:
self.lastName = name
self.birthday = None

def getName(self):
return self.name

def getLastName(self):
return self.lastName

def setBirthday(self, birthdate):
self.birthday = birthdate

def getAge(self):
if self.birthday == None:
raise ValueError('not set birthday')
return datetime.date.today().year-self.birthday.year

def __lt__(self, other):
if self.lastName == other.lastName:
return self.name < other.name
return self.lastName < other.lastName

def __str__(self):
return self.name

Exp3

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
class Student(Person):

nextIdNum = 0

def __init__(self, name):
Person.__init__(self, name)
self.idNum = Student.nextIdNum
Student.nextIdNum += 1

def getIdNum(self):
return self.idNum

def __lt__(self,other):
return self.idNum < other.idNum

class Grades:

def __init__(self):
self.students = []
self.grades = {}
self.isSorted = True

def addStudent(self, student):
if student in self.students:
raise ValueError('Duplicate student')
self.students.append(student)
self.grades[student.getIdNum()] = []
self.isSorted = False

def addGrade(self, student, grade):
try:
self.grades[student.getIdNum()].append(grade)
except:
raise ValueError('Student not in mapping')

def getGrades(self,student):
try:
return self.grades[student.getIdNum()][:]
except:
raise ValueError('Student not in mapping')

def getStudents(self):
if not self.isSorted:
self.students.sort()
self.isSorted = True
return self.students[:]

def gradeReport(self):
report = ''
for s in self.getStudents():
tot = 0.0
numGrades = 0
for g in self.getGrades(s):
tot += g
numGrades +=1
try:
average = tot/numGrades
report = report + '\n' + str(s) + '\'s mean grade is '+ str(average)
except ZeroDivisionError:
report = report + '\n' + str(s) + 'has no grade '
return report