• IO多路复用


    一、用非阻塞IO解决阻塞IO模型

      

    import socket
    sk = socket.socket()
    sk.bind(('127.0.0.1',8080))
    sk.listen()
    sk.setblocking(False)
    lst = []
    del_lst = []
    while 1:
        try:
            conn,address = sk.accept()
            lst.append(conn)
        except BlockingIOError:
            for conn in lst:
                try:
                    dat = conn.recv(1024).decode('utf-8')
                    if not dat:
                        del_lst.append(conn)
                        print('客户端正常关闭')
                        conn.close()
                    else:
                        print(dat)
                        conn.send(dat.upper().encode('utf-8'))
                except ConnectionResetError :
                    continue
                except BlockingIOError:
                    pass
            if del_lst:
                for i in del_lst:
                    lst.remove(i)
                del_lst.clear()
    sever_非阻塞IO解决IO阻塞
    import socket
    sk = socket.socket()
    sk.connect(('127.0.0.1', 8080))
    while 1:
        word = input('>>>')
        if word == 'q':
            break
        sk.send(word.encode('utf-8'))
        info = sk.recv(1024).decode('utf-8')
        print(info)
    
    sk.close()
    client_

    二、基于select的IO多路模型

    select  和  poll ,epoll

    select 和 poll 有一个共同机制:都采用轮询的方式去访问内核,问数据有没有准备好。

    select 有一个最大的监听事件的限制,32位机限制是1024,64位机限制是2048。

    poll 没有,理论上pool可以开启无限大

    epool 采用的是回调机制,解决了select 和 poll 的缺点

     二、用select解决IO阻塞

      代码:

      

    import socket
    import select
    
    sk = socket.socket()
    sk.bind(('127.0.0.1',8080))
    sk.listen()
    rlist = [sk]
    while 1:
        r, w, x = select.select(rlist, [], [])
        if r:
            for i in r:
                if i == sk:
                    conn,address = i.accept()
                    rlist.append(conn)
                else:
                    try:
                        dat = i.recv(1024).decode('utf-8')
                        if not dat:
                            print('客户端正常关闭')
                            rlist.remove(i)
                            i.close()
                        else:
                            print(dat)
                            i.send(dat.upper().encode('utf-8'))
                    except ConnectionResetError:
                        continue
    服务器代码(select)
    import socket
    sk = socket.socket()
    sk.connect(('127.0.0.1', 8080))
    while 1:
        word = input('>>>')
        if word == 'q':
            break
        sk.send(word.encode('utf-8'))
        info = sk.recv(1024).decode('utf-8')
        print(info)
    
    sk.close()
    客户端代码(select)

  • 相关阅读:
    报错Required String parameter 'customerInfo' is not present的原因及处理办法
    Mybatis 中$与#的区别
    ON DUPLICATE KEY UPDATE单个增加更新及批量增加更新的sql
    Git使用
    前后端分离
    对excel文件的读取
    POI导入和导出Excel总结
    git权限
    @RequestParam与@PathVariable
    lombok学习
  • 原文地址:https://www.cnblogs.com/wf123/p/9551544.html
Copyright © 2020-2023  润新知