forked from heyxiaohao/Python
-
Notifications
You must be signed in to change notification settings - Fork 0
/
面向对象.py
269 lines (193 loc) · 5.9 KB
/
面向对象.py
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
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
#!/usr/bin/env python
# -*- coding: utf-8 -*-
from _ast import Num
class Student(object): # object 是所有对象的基类
def __init__(self, name, score, id): # 构造函数
self.name = name
self.score = score
self.__id = id # 成员变量前加 __ 表示私有变量,无法从外部访问
def print_score(self):
print '%s, %s' % (self.name, self.score)
@property
def id(self):
return self.__id
@id.setter
def id(self, id):
self.id = id
bart = Student('Bart', 95.0, 1) # 实例化类
list = Student('List', 87.1, 2)
bart.print_score() # 成员函数调用
list.print_score()
bart.sex = '女' # 可以动态的添加属性,但是只对当前对象有效
print bart.sex
# print list.sex # 抛出异常AttributeError
print bart.name
#print bart.__id # 抛出异常AttributeError
print bart.id
class Animal(object):
def run(self):
print 'Animal is running...'
class Dog(Animal):
def run(self): # 覆盖父类方法
print 'Dog is running...'
def __len__(self): # 要获取自定义类型的len方法 需要自己编写 __len__()函数
return 3
class Cat(Animal):
def run(self):
print 'Cat is running...'
class Tortoise(Animal):
def run(self):
print 'Tortoise is running...'
dog = Dog()
cat = Cat()
dog.run()
cat.run()
def run_(animal):
animal.run()
run_(Dog())
run_(Cat())
run_(Tortoise())
# 获取对象信息
print '---获取对象信息---'
print type(123)
print type('abc')
print type([])
print type(str)
print type(Animal)
print type(dog)
# 每一种内置类型都在 types 模块有定义
import types
print type(123) == types.IntType
print type(Animal) == types.TypeType
# 判断类型 isinstance()
print '---isinatance()---'
print isinstance(dog, Animal)
print isinstance(dog, (Dog, Animal)) # 可以判断是否是中的一种类型
# 获取对象的所有属性和方法
print '---dir()---'
print dir(dog)
print len(dog)
# getattr() setattr() hasattr()
try:
print hasattr(bart, name)
except NameError:
pass
# 可以动态的给对象绑定属性
class A(object):
pass
print '---动态绑定属性---'
a = A()
b = A()
a.name = 'abc' # 仅对当前对象有效
print a.name
try:
print b.name
except AttributeError:
pass
print '---动态绑定方法---'
def set_age(self, age): # 定义方法体
self.age = age
from types import MethodType # 导入模块方法
a.set_age = MethodType(set_age, a, A) # 此方式只对当前实例有效
a.set_age(24)
print a.age
# 对所有实例都有效的动态绑定方法的方式 给类绑定
def set_score(self, score):
self.score = score
A.set_score = MethodType(set_score, None, A)
b.set_score(54)
print b.score
# 限制动态创建属性 __slots__ 变量 只对当前类有效,对子类无效
print '---限制---'
class B(object):
__slots__ = ('name', 'age')
c = B()
c.name = 'ad'
c.age = 12
try:
c.score = 'adf'
except AttributeError:
print 'AttributeError'
# @property 装饰器 将方法变为属性,可通过直接属性调用,并可检测参数值
print '---@property---'
class C(object):
def __init__(self):
self.__score = 10
def __len__(self):
return 9
@property # 只定义它,就只有getter
def score(self):
return self.__score
@score.setter
def score(self, value):
if not isinstance(value, int):
raise ValueError('score must be integer!')
if value < 0 or value > 100:
raise ValueError('score must be between 0 ~ 100')
self.__score = value
cc = C()
cc.score = 60
print cc.score
try:
cc.score = 9999
print cc.score
except ValueError:
print 'ValueError'
print len(cc)
# Python 支持多重继承
# 类 内置属性
print '类内置属性'
# __repr__ 打印实例的地址,但是对于用户而言无用,因此自定义__str__方法,让__repr__ = __str__
class D(object):
def __init__(self, name):
self.name = name
def __str__(self):
return 'D object (name = %s)' % self.name
__repr__ = __str__
print D('wangh')
# 如果需要将类 作为可迭代的对象,需要实现__iter__(self) 及 next(self) 方法
class E(object):
def __init__(self):
self.a = 0
self.b = 1
def __iter__(self):
return self
def next(self):
tmp = self.b
self.b = self.a + self.b
self.a = tmp
# self.a, self.b = self.b, self.a + self.b # 先计算在加上 同上
if self.a > 100000:
raise StopIteration()
return self.a
def __getitem__(self, n): # 使类可以使用索引取值, 但是需要对传入的参数做类型判断,如切片 isinstance(n, slice)
a, b = 1, 1
for x in range(n):
a, b = b, a + b
return a
# 还有负数等 与之对应的方法__setitem__ __delitem__
for n in E():
print n
print E()[10]
# 对实例进行调用 需要实现 __call__ 方法
class F(object):
def __init__(self, num):
self.num = num
def __call__(self):
return 'Num = %d' % self.num
f = F(123)
print f()
# callable 函数 可以判断 对象是否可以被调用
print callable(f)
# 使用 type()函数动态创建类
print '使用 type()函数动态创建类'
# 先定义函数
def fn(self, name = 'world'):
print 'Hello %s' % name
Hello = type('Hello', (object,), dict(hello = fn)) # 创建Hello class
h = Hello()
h.hello()
# 要创建类 type() 需要传入三个参数
# 1 class 的名称
# 2 继承的父类集合,如果只有一个 记住 元祖的 ,
# 3 方法名和函数绑定