面试题:BIO、NIO、AIO 的区别是什么?

文章目录


前言

今天这是我在教室分享的一道面试题,怕忘记了自己花时间去研究了一下,看了大量的资料后整理的,不收藏你们就亏了哟。


面试题:BIO,NIO,AIO的区别?

这是个网络编程的面试题:

在讲 BIO,NIO,AIO 之前先来回顾一下这样几个概念:同步与异步,阻塞与非阻塞。

同步

自己的理解:

也就是必须一件一件事做,等前一件做完了才能做下一件事 (提交请求->等待服务器处理->处理完返回 这个期间客户端浏览器不能干任何事 )

官方:

使用同步IO时,Java自己处理IO读写。

异步:

自己的理解:

请求通过事件触发->服务器处理(这是浏览器仍然可以作其他事情)->处理完毕

官方:

使用异步IO时,Java将IO读写委托给OS处理,需要将数据缓冲区地址和大小传给OS,完成后OS通知Java处理(回调)。

阻塞:

自己的理解:

阻塞就是说在煮水的过程中,你不可以去干其他的事情(性能和可靠性都不好)

官方:

使用阻塞IO时,Java调用会一直阻塞到读写完成才返回。

非阻塞:

自己的理解:

非阻塞就是在同样的情况下,可以同时去干其他的事情(对于低负载、低并发的应用程序)

官方:

使用非阻塞IO时,如果不能立马读写,Java调用会马上返回,当IO事件分发器通知可读写时在进行读写,不断循环直到读写完成。

IO的方式通常分为几种,同步阻塞的BIO、同步非阻塞的NIO、异步非阻塞的AIO。

一、传统的BIO(同步阻塞的BIO)

就是说服务端一旦接受客户端的连接,就可以建立通信套接字在这个通信套接字上进行读写操作,此时不能再接收其他客户端连接请求,只能等待同当前连接的客户端的操作执行完成,不过可以通过多线程来支持多个客户端的连接,循环导致高cpu消耗。

服务器的实现模式是一个连接一个线程,这样的模式很明显的一个缺陷是:

由于客户端连接数与服务器线程数成正比关系,可能造成不必要的线程开销,严重的还将导致服务器内存溢出。当然,这种情况可以通过线程池机制改善,但并不能从本质上消除这个弊端。

问题:当出现高并发怎么办?

解决这个问题就有了下面的

二、NIO(同步非阻塞的NIO)。它支持面向缓冲的,基于通道的I/O操作方法

从JDK1.4以后开始,JDK引入的新的IO模型NIO

  • Channel(通道) :通道是双向的,可读也可写,而流的读写是单向的。无论读写,通道只能和Buffer交互。因为 Buffer,通道可以异步地读写。
  • Buffer(缓冲区) :Buffer是一个对象,它包含一些要写入或者要读出的数据
  • Selector (选择器) :选择器用于使用单个线程处理多个通道。因此,它需要较少的线程来处理这些通道。线程之间的切换对于操作系统来说是昂贵的。因此,为了提高系统效率选择器是有用的。
    就是说加了三个功能来解决bio中的单线程一对多的问题

而服务器的实现模式是多个请求一个线程,即请求会注册到多路复用器Selector上,多路复用器轮询到连接有IO请求时才启动一个线程处理。

Java NIO: 单线程管理多个连接。

劣处:维护成本高,容易出现bug,项目大了之后消耗成本

三、AIO(异步非阻塞的AIO)

JDK1.7发布了NIO2.0也可以说是Nio的加强版,它是异步非阻塞的IO模型。

异步 IO 是基于事件和回调机制实现的,也就是应用操作之后会直接返回,不会堵塞在那里,当后台处理完成,操作系统会通知相应的线程进行后续的操作。

这就是真正意义上的异步非阻塞,服务器的实现模式为多个有效请求一个线程,客户端的IO请求都是由OS先完成再通知服务器应用去启动线程处理(回调)。

应用场景:并发连接数不多时采用BIO,因为它编程和调试都非常简单,但如果涉及到高并发的情况,应选择NIO或AIO,更好的建议是采用成熟的网络通信框架Netty。


总结:理解了这,浓缩了还是有点东西的

  • BIO是一个连接一个线程。

  • NIO是一个请求一个线程。

  • AIO是一个有效请求一个线程。

相关推荐
张张张31212 分钟前
4.2学习总结 Java:list系列集合
java·学习
KATA~15 分钟前
解决MyBatis-Plus枚举映射错误:No enum constant问题
java·数据库·mybatis
xyliiiiiL31 分钟前
一文总结常见项目排查
java·服务器·数据库
shaoing32 分钟前
MySQL 错误 报错:Table ‘performance_schema.session_variables’ Doesn’t Exist
java·开发语言·数据库
腥臭腐朽的日子熠熠生辉1 小时前
解决maven失效问题(现象:maven中只有jdk的工具包,没有springboot的包)
java·spring boot·maven
ejinxian1 小时前
Spring AI Alibaba 快速开发生成式 Java AI 应用
java·人工智能·spring
杉之1 小时前
SpringBlade 数据库字段的自动填充
java·笔记·学习·spring·tomcat
圈圈编码2 小时前
Spring Task 定时任务
java·前端·spring
俏布斯2 小时前
算法日常记录
java·算法·leetcode
27669582922 小时前
美团民宿 mtgsig 小程序 mtgsig1.2 分析
java·python·小程序·美团·mtgsig·mtgsig1.2·美团民宿