Skip to content

Commit 3f2ade0

Browse files
committed
猴子补丁
猴子补丁
1 parent 3ebb200 commit 3f2ade0

2 files changed

Lines changed: 61 additions & 0 deletions

File tree

python_basic/main.md

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -26,3 +26,4 @@
2626
* [\_\_new__()与\_\_init__()方法](new和init方法.md)
2727
* [@property 保护变量的访问与设置](保护变量的访问与设置.md)
2828
* [Python函数参数的传递机制](Python函数参数的传递机制.md)
29+
* [猴子补丁 monkey patch](猴子补丁.md)

python_basic/猴子补丁.md

Lines changed: 60 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,60 @@
1+
# 猴子补丁
2+
**monkey patch允许在运行期间动态修改一个类或模块**
3+
4+
* 在运行时替换方法、属性等
5+
* 在不修改第三方代码的情况下增加原来不支持的功能
6+
* 在运行时为内存中的对象增加patch而不是在磁盘的源代码中增加
7+
8+
```python
9+
class A:
10+
def func(self):
11+
print('这是A类下的func方法')
12+
13+
# arg 这个参数是没有用到的,因为func有一个参数,如果这个函数没有参数的话不能这样直接赋值
14+
def monkey_func(arg):
15+
print('这是猴子补丁方法')
16+
17+
if __name__ == '__main__':
18+
a = A()
19+
# 运行原类下的方法
20+
a.func() # 这是A类下的func方法
21+
22+
# 在不改变原类代码的情况下,动态修改原类的方法,打补丁
23+
A.func = monkey_func
24+
25+
# 运行替换后的方法
26+
a.func() # 这是猴子补丁方法
27+
```
28+
29+
## 应用
30+
gevent通过打补丁的方式,利用自己的socket替换了python的标准socket模块,利用gevent协程处理高并发的情况
31+
32+
```python
33+
from gevent import monkey
34+
monkey.patch_all()
35+
import gevent
36+
from socket import *
37+
38+
39+
def talk(conn):
40+
while 1: # 循环通讯
41+
try:
42+
from_client_msg = conn.recv(1024)
43+
if not from_client_msg:break
44+
print("来自客户端的消息:%s" %(from_client_msg))
45+
conn.send(from_client_msg.upper())
46+
except:
47+
break
48+
conn.close()
49+
50+
51+
if __name__ == '__main__':
52+
server = socket()
53+
ip_port = ("127.0.0.1", 8001)
54+
server.bind(ip_port)
55+
server.listen(5)
56+
while 1: # 循环连接
57+
conn, addr = server.accept()
58+
gevent.spawn(talk, conn) # 开启一个协程
59+
server.close()
60+
```

0 commit comments

Comments
 (0)