对NIO和BIO的进一步理解

news2024/12/28 3:46:25

疑问

在之前的学习中,只提到BIO是阻塞IO,在建立连接和读写事件时会阻塞线程。NIO是非阻塞IO,基于事件注册,通过Selector进行切换Channel,不会阻塞线程。对于这种解释,还是带有一些疑问的。Selector进行Channel的切换,是不阻塞线程了,但是Channel与操作系统之间的数据交换,是否阻塞线程呢?带着这种疑问,进一步理解了NIO知识,下面记录一下。

BIO的阻塞

在这里插入图片描述
应用程序采用BIO方式调用read()方法后,底层调用Linux系统的read方法,从内核缓冲区读取数据,如果内核缓冲区没有数据,那么该线程就一直阻塞,等到有数据,执行第二步,从内核缓冲区复制到用户缓冲区,然后返回数据。这两步全程阻塞。因此,使用BIO后,每个线程只要调用了read()方法,就会阻塞。这就是BIO的阻塞原理。

NIO的非阻塞

在这里插入图片描述
Linux系统提供了非阻塞的read()方法,NIO就是调用了这个方法,当内核缓冲区没有数据时,read()方法立即返回未就绪,不会阻塞线程。因此,应用程序需要轮询调用read()方法,直到有数据返回。所以,此步骤是非阻塞的。当内核缓冲区有数据时,调用read()方法,则从内核缓冲区复制数据到用户缓冲区,此步骤是阻塞执行的。这就是NIO的非阻塞原理。
那么NIO的非阻塞有何好处呢?好处就是当我们调用read()方法时,如果还没有数据,那么立即返回,不会阻塞线程,我们可以做一下其他的逻辑操作,然后过一段时间后,再调用read()方法,去获取数据,不至于一直在read()方法那里阻塞着,浪费了这个线程,什么都做不了。

NIO+IO多路复用

上面的NIO中,我们用轮询来多次调用read()方法,直到获取到读取的数据。而轮询带来的弊端就是CPU占用过高。因为提出了使用Linux系统提供的IO多路复用,来解决轮询带来的问题。

IO多路复用是一种同步IO模型, 是操作系统提供的能力, 使用少量线程监听Linux的多个IO文件描述符, 也就是线程复用于多个IO请求.
如果有任意IO文件描述符就绪, 就会告知应用进行读取,
如果没有IO文件描述符就绪, 就会阻塞应用线程.
Linux中, IO多路复用的实现是select/poll/epoll

在这里插入图片描述
Linux提供的IO多路复用,可以用最少的线程,来处理多个IO请求。因此,在第一个阶段,使用Linux的多路复用机制,用很少的线程去监测多个IO连接。当监测的IO连接都没有发生IO事件时,监测线程也会发生阻塞。当某个连接发生IO事件后,通知应用程序有数据可读,此时应用程序才会调用read()方法。
调用read()方法后,就和上面NIO的操作一样了,从内核缓冲区复制到用户缓冲区,返回给应用程序,此过程是阻塞的。

上面提到,当被监测的请求没有发生IO事件时,也是阻塞的,那和BIO的阻塞有何区别呢?
在NIO+多路复用中,使用了Linux的多路复用机制,很少的线程就可以监测多个IO事件,而且是专门的线程去监测IO事件。即使在监测阶段发生阻塞,也是很少的线程被阻塞,且应用程序的线程不会被阻塞,不影响应用程序的运行。而BIO的阻塞是对应用程序的阻塞。这样区别就很明显了。所以NIO+IO多路复用是网络连接中提高性能的解决方案。

在之前写到的java提供的NIO的API,就是采用了NIO+IO多路复用的机制实现的。

Liunx的epoll

简单来说就是采用注册回调机制, 替代了轮询遍历,利用mmap减少了文件描述符在用户空间和内核空间的拷贝,因此性能高。具体详情另作研究。

参考文章:彻底理解非阻塞IO(NIO)

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/157544.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

#define 实现快捷模板类实例在eigen::Maxtrix中的应用

欢迎关注更多精彩 关注我&#xff0c;学习常用算法与数据结构&#xff0c;一题多解&#xff0c;降维打击。 背景 在eigen库中&#xff0c;矩阵类原来的用法是 Matrix<Type, row, col>。 为了方便用户&#xff0c;库中还提供了用户常用的快捷类型&#xff0c;比如Matrix…

Java-String的API

一、length()package 做题; import java.lang.reflect.Array; import java.security.PublicKey; import java.util.Arrays; import java.util.Scanner;import javax.naming.StringRefAddr;public class Main {public static void main(String[] args) {Scanner sc new Scanne…

ZeroTierr的moon云服务器搭建和使用

搭建moon 问题是ZeroTier One本身的服务器都在国外访问速度很慢。可以通过搭建国内Moon服务加速解决连接慢的问题。 1、 进入云服务器在线安装zerotier curl -s https://install.zerotier.com/ | sudo bash查看安装zerotier版本 sudo zerotier-cli status安装完成后生成moon…

从0到1完成一个Vue后台管理项目(二十二、列表拖拽排序SortableJS)

往期 从0到1完成一个Vue后台管理项目&#xff08;一、创建项目&#xff09; 从0到1完成一个Vue后台管理项目&#xff08;二、使用element-ui&#xff09; 从0到1完成一个Vue后台管理项目&#xff08;三、使用SCSS/LESS&#xff0c;安装图标库&#xff09; 从0到1完成一个Vu…

Python WebGL 3D应用开发快速入门

在本文中&#xff0c;我们将学习如何在Python中使用three.js库&#xff0c;而无需编写任何一行 JavaScript。我们将使用PyWeb3D&#xff0c;这是一个额外的层&#xff0c;旨在与Brython的three.js轻松交互。 1、什么是PyWeb3D&#xff1f; 简单地说&#xff0c;PyWeb3D是一个…

现代JavaScript,你应该使用的10件事

javascripttip&#xff08;3 部分系列&#xff09;1现代 JavaScript&#xff0c;你应该使用的 10 件事&#xff0c;从今天开始2了解如何在 JavaScript 中使用循环3如何在 JavaScript 中学习足够多的 RegEx 才能变得危险您可能对 JavaScript 完全陌生&#xff0c;也可能多年来只…

文件学习笔记

删除线格式 ## 文件描述符 1.文件文件内容文件属性。 2.文件操作文件内容的操作文件属性的操作。 3.所谓的“打开”文件&#xff0c;是指将文件的属性或内容加载到内存中—这是由冯诺依曼决定。 4.所以文件不全打开&#xff0c;不打开的文件放在磁盘存储。 5.内存文件&#xff…

在线教育-谷粒学院学习笔记(三)

文章目录1 搭建前端项目环境2 前端页面框架介绍3 讲师管理前端开发4 后台系统登录功能改造到本地5 前端框架开发过程6 讲师列表前端实现7 讲师分页前端实现8 讲师条件查询前端实现9 讲师删除功能前端实现10 讲师添加前端实现11 讲师修改前端实现12 前端路由切换问题解决1 搭建前…

Linux工具学习之【gdb】

✨个人主页&#xff1a; Yohifo &#x1f389;所属专栏&#xff1a; Linux学习之旅 &#x1f38a;每篇一句&#xff1a; 图片来源 &#x1f383;操作环境&#xff1a; CentOS 7.6 阿里云远程服务器 Whatever is worth doing is worth doing well. 任何值得去做的事情&#xff0…

【HTML】一款可交互的响应式登陆注册表单,你确定不来看看嘛(附源码)

&#x1f482;作者简介&#xff1a; THUNDER王&#xff0c;一名热爱财税和SAP ABAP编程以及热爱分享的博主。目前于江西师范大学会计学专业大二本科在读&#xff0c;同时任汉硕云&#xff08;广东&#xff09;科技有限公司ABAP开发顾问。在学习工作中&#xff0c;我通常使用偏后…

2022年五一杯数学建模C题火灾报警系统问题求解全过程论文及程序

2022年五一杯数学建模 C题 火灾报警系统问题 原题再现&#xff1a; 二十世纪90年代以来&#xff0c;我国火灾探测报警产业化发展非常迅猛&#xff0c;从事火灾探测报警产品生产的企业已超过100家&#xff0c;年产值达几十亿元&#xff0c;已经成为我国高新技术产业的一个组成…

Docker之Nginx部署前端项目

目录 创建nginx容器 nginx.conf讲解 ①所有配置必须以“;”结尾 ②nginx发布java项目 nginx发布静态vue项目 nginxtomcat实现反向代理及均衡 nginxhtml静态服务器 创建nginx容器 docker run –name mynginx -d -p 80:80 -v /data/nginx/conf/nginx.conf:/etc/nginx/ngin…

6款强烈推荐的 SD卡/内存卡数据恢复软件

SD卡/内存卡在 21 世纪的作用比以往任何时候都更加重要。众所周知&#xff0c;SD卡/内存卡具有高数据传输率并且是便携式设备&#xff0c;大多数摄影师甚至智能手机用户主要依靠它们来保存所有个人或项目照片和视频。此外&#xff0c;SD 卡还因其与各种设备的兼容性而广受欢迎。…

JUC并发编程学习笔记——AQS个人理解

1. AQS引出 1.1 前置知识&#xff1a; 线程创建的四种方式&#xff1a;Thread、Runnable、callable、线程池 LockSupport的使用&#xff1a;park()和unpark()方法 LockSupport是一个工具类&#xff0c; 提供了基本的线程阻塞和唤醒功能&#xff0c;它是创建锁和其他同步组件的…

使用 NVIDIA NeuralVDB优化大规模稀疏

使用 NVIDIA NeuralVDB优化大规模稀疏 基于 OpenVDB 过去十年的发展&#xff0c;NVIDIA NeuralVDB 的推出对于处理极其庞大和复杂的数据集的开发人员和研究人员来说是一个游戏规则的改变者。 NVIDIA NeuralVDB 的预发布版本为 OpenVDB 带来了 AI 和 GPU 优化&#xff0c;将烟雾…

【OpenCV】:OpenCV人脸识别项目杂记

项目目标&#xff1a; 1.图片人脸识别 2.视频人脸识别 3.ESP32Cam摄像头网页视频人脸识别 项目效果视频&#xff1a; ESP32Cam摄像头人脸识别OpenCV本地视频人脸识别ESP32Cam摄像头人脸检测项目基础代码内容&#xff1a; 一、读取图片 # 导入cv模块 import cv2 as cv# 读取图…

如何设置Excel表格以“只读模式“打开

设置Excel表格以“只读模式”打开&#xff0c;可以防止意外修改表格内容&#xff0c;因为“只读模式”下的Excel无法直接保存&#xff0c;这样就不用担心表格意外修改&#xff0c;关闭时又不小心保存了。 这个模式我们可以通过“另存为”的方法来设置。 打开Excel表格后&…

【学习笔记之Linux】工具之gcc/g++

背景知识&#xff1a; gcc/g是一个编译器&#xff0c;注意区分编译器和编辑器&#xff0c;vim是是编辑器。简单的说&#xff0c;编辑器是我们敲代码的工具&#xff0c;我们在编辑器上写出我们需要实现的功能&#xff1b;编译器负责实现功能&#xff0c;把我们写的高级语言编译成…

马蹄集 古人的剩余定理

古人的剩余定理 难度&#xff1a;白银 ©时间限制&#xff1a;1秒 巴占用内存&#xff1a;64M 今有物不知其数&#xff0c; 三三数之剩二&#xff0c; 五五数之剩三&#xff0c; 七七数之剩二。 问物最少几何&#xff1f; #include <bits/stdc.h> using nam…

使用Paddle飞桨重写波士顿房价预测案例

1.Paddle飞桨设计之“道” 当读者使用飞桨框架编写多个深度学习模型后&#xff0c;会发现程序呈现出“八股文”的形态。即不同的程序员、使用不同模型、解决不同任务的时候&#xff0c;他们编写的建模程序是极其相似的。虽然这些设计在某些“极客”的眼里缺乏精彩&#xff0c;…