2016-01-13 148 views
2

现在我有两个线程,线程1是主线程和线程2是thread.I需要线程2做的所有网络问题的任务,所以我把所有的插座中的线程2,并将其设置为无堵塞。线程1用于将请求推送到线程2来完成这项工作。蟒蛇异步Socket编程

起初,我写的是这样的:

request_queue = Queue.Queue() 
tasks = [] 
sockets = [] 

**thread 1:** 

while True: 

    get_user_input() 
    #... 
    request_queue.put(request_task) 

**thread 2:** 

while True: 

    if have_requests(request_queue): 

     t = create_task() 

     tasks.append(t) 

     sockets.append(t.socket()) 

    select(sockets,timeout=0) #no blocking select 

    update_tasks() 
    #... 

显然,当没有请求和任务,线程2会浪费cpu.I不想使用睡眠(),因为当线程2睡觉,它无法处理请求在time.Then我想,也许我应该request_queue更改为本地主机插座,这样的:

request_queue = sock.sock() 
request_queue.bind(local_host,some_port) 
request_queue.listen() 

**thread 1** 

while True: 

    get_user_input() 

    request_queue.send(new_request) 


**thread 2** 

while True: 

    select(sockets) # blocking select 

    if request_queue is active: 
     t = request_queue.recv() 
     t = create_task(t) 
     tasks.append(t) 
     sockets.append(t.socket()) 

    #check other sockets 
    #update tasks... 

但这样子有点棘手,我不知道是否这是一个好方法。我想要的是线程2可以及时处理请求,不要浪费CPU时间并在同一时间处理套接字事件。任何人都可以帮忙

+0

为什么Thread2不是从队列中简单地[消耗道具](https://docs.python.org/3/library/queue.html#queue.Queue.get)? (阻塞) – Pynchia

+0

因为它创建队列任务物品,然后将处理套接字事件了。 –

回答

1

对于异步网络,请参阅TornadoTwistedGevent。也this article可能是有用的为您服务。 实例与GEVENT:

def handle_socket(sock): 
    sock.sendall("payload") 
    sock.close() 

server = socket.socket() 
server.bind(('0.0.0.0', 9999)) 
server.listen(500) # max connections 
while True: 
    try: 
     new_sock, address = server.accept() 
    except KeyboardInterrupt: 
     break 
    # handle every new connection with a new handler 
    gevent.spawn(handle_socket, new_sock) 

而且Celery是最合适的后台作业执行。

+1

我想要做的更像是一个线程池等待请求,而不是服务器。我会在稍后阅读。 –

+2

....或只是https://docs.python.org/3/library/asyncio.html? – xtofl

+1

是的,如果我写一个服务器,那么这是很好的。但现在,我需要服务器同时处理来自其他线程和异步套接字事件的新请求。顺便说一下,我使用的是Python 2.7。 –