NonBlocking 非阻塞IO 状态下的实现单线程协程socket通信

# 服务器端

# -*- coding: utf-8 -*-
import time
from socket import *

server = socket(AF_INET,SOCK_STREAM)
server.bind(('127.0.0.1',8081))
server.listen(5)
server.setblocking(False) # 至关重要的一步!!!
conn_l = []
print('waiting...')
while True:
    try:
        print(f'total connections {len(conn_l)}')
        time.sleep(2)
        conn,addr = server.accept()
        conn_l.append(conn)

    # 对于整个大的while 循环来说,一直都没有结束,如果while里面的try条件成立,conn_l列表的值加1
    # 对于下一次循环来说,如果try的条件不成立,则对于conn_l列表来说,会再一次尝试接收数据,如果有收到就继续执行,没有收到就pass
    # 为什么对于conn_l 列表的长度改变了,但是却没有报错,对于for 循环,改变了循环条件? 在外部while 循环可以改,在循环的时候不要修改
    # 的确能实现单线程下的并发,但是死循环,对CPU的占用率会变高,
    except BlockingIOError:
        del_l = []
        for conn in conn_l:
            try:
                data = conn.recv(1024)
                if len(data) == 0:
                    del_l.append(conn)
                    continue
                conn.send(data.upper())
            except BlockingIOError:
                pass
            except ConnectionResetError:
                del_l.append(conn)

        for conn in del_l:
            conn_l.remove(conn)

# 客户端
# -*- coding: utf-8 -*-
import os
from socket import *

client = socket(AF_INET, SOCK_STREAM)
client.connect(('127.0.0.1',8081))


while True:
    msg = f" {os.getpid()} say hello"
    client.send(msg.encode('utf-8'))
    data = client.recv(1024)
    print(data.decode('utf-8'))

posted @ 2023-04-01 22:51  MrSphere  阅读(48)  评论(0)    收藏  举报