0、承上

  进程:

    计算机里最小的资源分配单位;

    数据隔离, 利用多核,数据不安全。

  线程:

    计算机中最小的CPU调度单位;

    数据共享,GIL锁,数据不安全.

  协程:

    线程的一部分,是有用户来调度的;

    数据共享,数据安全.

  异步:  同时做不止一件事情.

  同步:  事情一件接着一件 的做.

  阻塞:  recv、recvfrom、accept、sleep、input

  非阻塞:平时遇见的处过上边基本上都是。

  IO操作:

    网络相关的操作

    文件处理、json.dump/load、logging、print、input、recv/send、connect/accept、recvfrom/sendto

  recv为什么要阻塞?

    等待数据到来到Python程序的内存中。

  IO模型一共有五种,由于信号驱动IO不常用,我们这里主要介绍阻塞IO、非阻塞IO、IO多路复用以及异步IO。

  对于一个network IO(这里以read举例),它会涉及到两个系统对象,一个是调用这个IO的process(or thread),另一个就是系统内核(kernel).当一个read操作发生时,该操作会经历两个阶段:

    (1)  等待数据准备( Waiting for the data to be ready )

    (2)  将数据从内核拷贝到进程中( Copying the data from the kernel to the process )

  这些IO模型的区别就在这两个阶段上各有不同.

1、阻塞IO( Blocking IO )

  在Linux中,默认情况下所有的socket都是blocking读操作流程大概如下:

 import socket

 sk = socket.socket()
sk.setblocking(True) # True 阻塞
# False 非阻塞
# TCP协议的socket sever不能同时接收多个请求
# sk.accept()
# while True:
# conn.recv()

2、非阻塞IO(non-blocking IO)

  非阻塞的形式实现了并发的socket server.

  非阻塞的形式实现了并发的socket sever,太耗CPU.

  没有数据来的时候程序的高速处理极大地占用了CPU资源.

 import socket

 sk = socket.socket()
sk.bind(('127.0.0.1', 9000))
sk.setblocking(False)
sk.listen()
conn_lst = []
del_lst = []
while True:
try:
conn,addr = sk.accept() # 非阻塞,没有连接来就报错
conn_lst.append(conn)
print(conn)
except BlockingIOError:
for con in conn_lst:
try:
con.send(b'hello')
try:
print(con.recv(1024)) # 非阻塞 没有消息来就报错
except BlockingIOError: # 没有消息就报错
pass
except ConnectionResetError: # send没有连接的报错
con.close()
del_lst.append(con)
for con in del_lst:
conn_lst.remove(con)
del_lst.clear()

服务器端

 import socket

 sk = socket.socket()
sk.connect(('127.0.0.1', 9000))
while True:
print(sk.recv(1024))
sk.send(b'bye')
sk.close()

客户端

  sever:

结果:

D:\Python36\python.exe E:/Python/草稿纸0.py
<socket.socket fd=268, family=AddressFamily.AF_INET, type=SocketKind.SOCK_STREAM, proto=0, laddr=('127.0.0.1', 9000), raddr=('127.0.0.1', 51839)>
b'bye'
b'byebye'
b'bye'
b'bye'
b'bye'
b'bye'
b'bye'
b'bye'
b'bye'
b'bye'
b'bye'
b'bye'
b'bye'
b'bye'
b'bye'
b'bye'
b'bye'
b'bye'
b'bye'
b'bye'
b'bye'
b'bye'
b'bye'
b'bye'
b'bye'
b'bye'
b'bye'
b'bye'
b'bye'
b'bye'
b'bye'
b'bye'
b'byebye'
b'bye'
b'bye'
b'bye'
b'byebye'
b'bye'
b'bye'
b'bye'
b'bye' Process finished with exit code 1

服务器端

D:\Python36\python.exe E:/Python/草稿纸.py
b'hello'
b'hello'
b'hello'
b'hello'
b'hello'
b'hello'
b'hello'
b'hello'
b'hello'
b'hello'
b'hello'
b'hello'
b'hello'
b'hello'
b'hello'
b'hello'
b'hello'
b'hello'
b'hello'
b'hello'
b'hello'
b'hello'
b'hello'
b'hello'
b'hello'
b'hello'
b'hello'
b'hello'
b'hello'
b'hello'
b'hellohellohello'
b'hello'
b'hello'
b'hellohellohello'
b'hello'
b'hello'
b'hellohellohellohellohellohellohellohellohellohellohellohellohellohellohellohellohellohellohellohellohellohellohellohellohellohellohellohellohellohellohellohellohellohellohellohellohellohello'
b'hellohello'
b'hello'

客户端结果

  由于通信的一直是小数据块(大小不够1024),出现了黏包现象.

3、IO多路复用(IO multiplexing)

 import select
import socket sk = socket.socket()
sk.bind(('127.0.0.1', 9000))
sk.setblocking(False)
sk.listen() rlst = [sk] # 监听的是对象的读操作
wlst = [] # 监听的是对象的写操作
xlst = [] # 监听的是对象的异常操作
while True:
rl,wl,xl = select.select(rlst, wlst, xlst)
for obj in rl:
if obj == sk:
conn,addr = sk.accept()
rlst.append(conn)
else:
msg = obj.recv(1024)
if msg == b'':
obj.close()
rlst.remove(obj)
continue
print(msg)
obj.send(b'hello')

IO多路复用-sever端

 import socket

 sk = socket.socket()
sk.connect(('127.0.0.1', 9000))
while True:
sk.send(b'wahaha')
print(sk.recv(1024))
sk.close()

IO多路复用-client端

  socketsever —— TCP协议的并发操作  selectors + 多线程

  IO多路复用的select的工作机制

    select  Windows  轮询

    poll      Linux        轮询,poll能够监听的对象比select要多

    epoll    Linux        不是采用轮询的方式,而是采用回调函数的形式

Python_阻塞IO、非阻塞IO、IO多路复用的更多相关文章

  1. IO多路复用,同步,异步,阻塞和非阻塞 区别

    一.什么是socket?什么是I/O操作? 我们都知道unix(like)世界里,一切皆文件,而文件是什么呢?文件就是一串二进制流而已,不管socket,还是FIFO.管道.终端,对我们来说,一切都是 ...

  2. IO多路复用,同步,异步,阻塞和非阻塞 区别(转)

    转自:http://www.cnblogs.com/aspirant/p/6877350.html?utm_source=itdadao&utm_medium=referral 同步.异步 是 ...

  3. IO模型--阻塞IO,非阻塞IO,IO多路复用,异步IO

    IO模型介绍: * blocking IO 阻塞IO * nonblocking IO 非阻塞IO * IO multiplexing IO多路复用 * signal driven IO 信号驱动IO ...

  4. Python网络编程-IO阻塞与非阻塞及多路复用

    前言 问题:普通套接字实现的服务端的缺陷 一次只能服务一个客户端!                         accept阻塞! 在没有新的套接字来之前,不能处理已经建立连接的套接字的请求 re ...

  5. python 全栈开发,Day44(IO模型介绍,阻塞IO,非阻塞IO,多路复用IO,异步IO,IO模型比较分析,selectors模块,垃圾回收机制)

    昨日内容回顾 协程实际上是一个线程,执行了多个任务,遇到IO就切换 切换,可以使用yield,greenlet 遇到IO gevent: 检测到IO,能够使用greenlet实现自动切换,规避了IO阻 ...

  6. {python之IO多路复用} IO模型介绍 阻塞IO(blocking IO) 非阻塞IO(non-blocking IO) 多路复用IO(IO multiplexing) 异步IO(Asynchronous I/O) IO模型比较分析 selectors模块

    python之IO多路复用 阅读目录 一 IO模型介绍 二 阻塞IO(blocking IO) 三 非阻塞IO(non-blocking IO) 四 多路复用IO(IO multiplexing) 五 ...

  7. 同步和异步 阻塞和非阻塞 IO多路复用和select总结

    同步和异步的概念 同步是指用户线程发起IO请求后,需要等待或者轮询内核IO操作完成后才能继续执行: 异步是指用户线程发起IO请求后仍继续执行,当内核IO操作完成后会通知用户线程或者调用用户线程注册的回 ...

  8. (IO模型介绍,阻塞IO,非阻塞IO,多路复用IO,异步IO,IO模型比较分析,selectors模块,垃圾回收机制)

    参考博客: https://www.cnblogs.com/xiao987334176/p/9056511.html 内容回顾 协程实际上是一个线程,执行了多个任务,遇到IO就切换 切换,可以使用yi ...

  9. IO阻塞模型、IO非阻塞模型、多路复用IO模型

    IO操作主要包括两类: 本地IO 网络IO 本地IO:本地IO是指本地的文件读取等操作,本地IO的优化主要是在操作系统中进行,我们对于本地IO的优化作用十分有限 网络IO:网络IO指的是在进行网络操作 ...

  10. 网络IO之阻塞、非阻塞、同步、异步总结

    网络IO之阻塞.非阻塞.同步.异步总结 1.前言 在网络编程中,阻塞.非阻塞.同步.异步经常被提到.unix网络编程第一卷第六章专门讨论五种不同的IO模型,Stevens讲的非常详细,我记得去年看第一 ...

随机推荐

  1. python3 requests + BeautifulSoup 爬取阳光网投诉贴详情实例代码

    用到了requests.BeautifulSoup.urllib等,具体代码如下. # -*- coding: utf-8 -*- """ Created on Sat ...

  2. NodeJS二进制包安装和快捷键配置(适用于U盘版安装配置)

    首先下载NodeJS二进制安装包:https://nodejs.org/dist/v10.15.3/node-v10.15.3-win-x64.zip 在D盘新建NodeJS文件夹,解压node-v1 ...

  3. Servlet(一):Hello Servlet

    今天介绍的专题是servlet和jsp,属于web开发中的基础,先来实际操作一下servlet,创建你的第一个web小项目. 1.新建一个maven项目. 鼠标右键单击eclipse左边项目栏的空白区 ...

  4. June 11. 2018 Week 24th, Monday

    Love is the beauty of the soul. 爱是灵魂之美. From Saint Augustine. The complete version of this quote goe ...

  5. css点滴2—六种方式实现元素水平居中

    本文参考文章<六种方式实现元素水平居中> 元素水平居中的方法,最常见的莫过于给元素一个显式的宽度,然后加上margin的左右值为auto.这种方式给固定宽度的元素设置居中是最方便不过的.但 ...

  6. C++_调用约束

    1.要求 声明定义处调用约定必须相同 int __stdcall add(int a, int b); int __stdcall add(int a, int b) {  return a + b; ...

  7. 阿里八八Beta冲刺博客集合贴

    Scrum 阿里八八β阶段Scrum(1/5) 阿里八八β阶段Scrum(2/5) 阿里八八β阶段Scrum(3/5) 阿里八八β阶段Scrum(4/5) 阿里八八β阶段Scrum(5/5) 总结 阿 ...

  8. 用栈来实现队列的golang实现

    使用栈实现队列的下列操作: push(x) -- 将一个元素放入队列的尾部. pop() -- 从队列首部移除元素. peek() -- 返回队列首部的元素. empty() -- 返回队列是否为空. ...

  9. 基于python的Selenium使用小结

    之前介绍过基于Unittest和TestNG自动化测试框架,然而基于Web端的测试的基础框架是需要Selenium做主要支撑的,这里边给大家介绍下Web测试核心之基于Python的Selenium 一 ...

  10. (转)Spring Boot 2 (二):Spring Boot 2 尝鲜-动态 Banner

    http://www.ityouknow.com/springboot/2018/03/03/spring-boot-banner.html Spring Boot 2.0 提供了很多新特性,其中就有 ...