【发布时间】:2014-06-08 13:50:40
【问题描述】:
我发现 python 网络慢。
我有一个服务器(用 C 编写)。我用我的客户端(python)对其进行了测试。
我可以联系到2MB/s。这让我很担心,所以我检查了这个:
host1(客户端):
cat some_big_file | nc host2 9999
host2(服务器):
nc -l 0.0.0.0 9999 | pv > /dev/null
我达到了大约 120MB/s (1Gb) 的速度。
服务器不是瓶颈,我们在生产中使用它,它可以处理更多。但可以肯定的是,我复制了简单的 python gevent 服务器进行测试。它看起来像这样:
#!/usr/bin/env python
from gevent.server import StreamServer
from gevent.pool import Pool
def handle(socket, address):
while True:
print socket.recv(1024)
pool = Pool(20000)
server = StreamServer(('0.0.0.0', 9999), handle, spawn=pool)
server.serve_forever()
下一个措施是从nc (host1) 发送到gserver (host2)。
主机1:cat some_big_file | nc host2 9999
主机2:./gserver.py | pv > /dev/null
host2 上的输出:[ 101MB/s]。还不错。
但是,当我使用我的 python 客户端时,它仍然很慢。我将客户端切换到gevent。我尝试了几个greenlets。 1, 10, 100, 1000 - 它没有太大帮助,我可以用一个 python 进程达到20MB/s 或~30MB/s 2、3、4、5 个单独的 python 进程,这是一些东西,但仍然不是那么好)。还是很慢。我已经把客户端改成笨蛋了,像这样:
#!/usr/bin/env python
import sys
import socket
c = socket.create_connection((sys.argv[1], sys.argv[2]))
while 1:
c.send('xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx\n')
通过这种方法,我可以联系到10MB/s。我还尝试了将整个大 2GB 文件读取到内存并将其发送的方法,类似的结果。
我还尝试将 python 脚本作为单独的进程运行(使用tmux)。如果我使用 1 个进程,我可以达到 10MB/s,2 个进程 20MB/s,3 个进程 23MB/s,4、5、6 个进程没有改变任何东西(使用 gevent 版本和简单的版本进行测试)。
详情: Python-2.7.3 Debian 7 - 标准安装 机器是 AWS 实例,客户端是 c1.medium,服务器是 c3.xlarge。 nc 和 iperf 在机器之间测得 1Gb/s。
问题:
- 为什么我使用 python 服务器(gevent 服务器)可以快速接收大量数据,但即使 C 程序可以,也不能以相同的速度发送。
- 为什么将进程加倍不会将发送速度提高到极限,只会提高到某个值。
- 有什么方法可以在 python 中使用套接字快速发送数据?
【问题讨论】:
-
"I am finding python networking slow"。不,您发现 您的应用程序(恰好是用 Python 编写的)速度很慢。 -
@JonathonReinhart 是的,你是对的......但我尝试了不同的方法,因此有了这条捷径。
标签: python performance sockets python-2.7 network-programming