BIO,NIO,AIO,IO多路复用都是什么意思?

写在前面

在这里插入图片描述
本文一起看下都有哪些不同的IO模型,以及不同IO模型的特点和优缺点是什么。

1:阻塞非阻塞,异步和同步

阻塞和非阻塞,异步和同步是在含义上非常接近的概念,很容易混淆,我也不能保证完全理解到位,这里分享下自己的理解,有不正确的地方还请留言指正。

  • 阻塞和非阻塞
    站在应用程序的角度看,如果是发起IO调用后,应用程序线程会阻塞一直等到获取响应则就是阻塞IO,反之应用程序可以执行其他任务,而不阻塞等待则就是非阻塞IO。

  • 异步和同步
    站在系统的角度看,同步就是,在收到应用程序的IO请求后,系统不会立即返回响应,而是在处理完成后,才通过系统调用告知应用程序IO结果,异步就是系统收到应用程序的IO请求后,会直接告知应用程序IO请求已收到,之后异步开始处理,处理完成后,通过回调的方式告知应用程序处理结果。比如系统调用read就是同步读,在没有读到数据之前,系统不会响应应用程序。比如系统调用aio_read就是异步读,系统收到AIO的读请求后,直接返回,最终读取的结果会异步回调应用程序。

通过以上分析可以看到,阻塞和非阻塞是站在应用程序的角度看的,而同步和异步是站在系统的角度看到。

2:BIO

即Blocking IO,是一种同步阻塞的IO模型,每次read操作获取数据,会一直等待直到内核获取数据然后将数据拷贝到用户内存空间,这种IO模型的最大优点是不会浪费CPU资源,但是这种IO模型在高并发场景中并不适用,因为存在严重的性能问题。

3:NIO

注意不是Java NIO,Java的NIO是New IO,和这里分析的不是一回事,Java NIO使用的线程模型是IO多路复用。

这里的N是Non-blocking的意思,全称是Non-blocking IO,非阻塞IO, 但还是同步的,所以是同步非阻塞IO。不同于BIO,NIO模型在执行read操作时,当内核没有可以读取的数据时,会直接返回,这样用户线程就可以先执行其他任务了,之后会定时的执行read,查看内核是否有数据可读取,这个过程可参考下图:

在这里插入图片描述

NIO这种IO模型的最大问题是read轮询,这会导致占用大量的CPU时间片,降低CPU的利用率,在高并发场景下这种IO模型也并没有用武之地,而且因为是轮询,也会造成响应延迟增大的问题,从而会降低系统的吞吐量。

4:IO多路复用模型

是一种阻塞异步IO模型,是一种单个线程处理多个连接的IO模型,相比于BIO,NIO,只有read操作,IO多路复用模型增加了select操作,该操作也是一个阻塞操作,当存在某个socket fd,即某个连接可以进行读取数据的操作是,select函数返回,然后执行read操作获取数据,这个read获取数据操作的过程也是阻塞的,这个过程如下图:

在这里插入图片描述

当前Linux对于多路复用模型提供的具体支持有select,poll,epoll,其中后者都是前者的升级版本,目前使用最多的就是epoll。内核需要维护一组fd,当存在某fd可读数据时,select函数就返回可读连接,然后read读取操作,如果是具体的用户操作速度非常快的话,这种基于单线程的IO模型,性能上也是不会差的,比如redis就是基于此IO模型实现的数据操作。

5:AIO

A,Asynchronous,异步,即Asynchronous IO,异步IO,是唯一的一种异步非阻塞的IO模型,执行read操作后,线程就返回执行其他任务了,后续的数据准备,从内核控件拷贝到用户空间的操作,全部由内核完成,数据拷贝完成后调用应用程序注册的回调程序,将数据交给应用程序处理,参考下图:

在这里插入图片描述

写在后面

参考文章列表:

Java并发之BIO NIO AIO IO多路复用的区别

评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值