当前位置: 首页 > news >正文

BIO和NIO编程(待完善)

目录

IO模型

BIO

NIO

常见问题


IO模型

Java共支持3种网络编程IO模式:BIO,NIO,AIO

BIO

同步阻塞模型,一个客户端连接对应一个处理线程

代码示例:

 Server端:

public class BioServer {private static ExecutorService executorService = Executors.newFixedThreadPool(10);public static void main(String[] args) throws IOException {ServerSocket serverSocket = new ServerSocket(8888);System.out.println("服务器启动成功");while (true) {Socket socket = serverSocket.accept();System.out.println("客户端连接成功");executorService.execute(() -> {try (BufferedReader reader = new BufferedReader(new InputStreamReader(socket.getInputStream()));BufferedWriter writer = new BufferedWriter(new OutputStreamWriter(socket.getOutputStream()))) {String message;while ((message = reader.readLine()) != null) {System.out.println("收到消息: " + message);writer.write("已收到消息: " + message);writer.newLine();writer.flush();}} catch (IOException e) {e.printStackTrace();}});}}
}

Client端:

public class BioClient {public static void main(String[] args) throws IOException {Socket socket = new Socket("localhost", 8888);BufferedWriter writer = new BufferedWriter(new OutputStreamWriter(socket.getOutputStream()));BufferedReader reader = new BufferedReader(new InputStreamReader(socket.getInputStream()));BufferedReader consoleReader = new BufferedReader(new InputStreamReader(System.in));String message;while ((message = consoleReader.readLine()) != null) {writer.write(message);writer.newLine();writer.flush();System.out.println("发送消息: " + message);System.out.println("收到回复: " + reader.readLine());}socket.close();}
}

执行结果:

存在问题:

  • IO操作是阻塞操作, 连接时读写会造成线程阻塞
  • 线程太多会造成CPU异常

应用场景:

        BIO 方式适用连接数较小且固定的架构, 这种方式对服务器资源要求比较高, 但代码简单易理解。

NIO

        同步非阻塞,服务器实现模式为一个线程可以处理多个请求(连接),客户端发送的连接请求都会注册到多路复用器selector上,多路复用器轮询到连接有IO请求就进行处理,JDK1.4开始引入。

应用场景:

        NIO方式适用于连接数目多且连接比较短(轻操作) 的架构, 如聊天服务器, 弹幕系统, 服务器间通讯,编程比较复杂。

代码

public class BioSelectorServer {public static void main(String[] args) throws IOException {ServerSocketChannel serverSocket = ServerSocketChannel.open();serverSocket.socket().bind(new InetSocketAddress(9000));// 设置非阻塞serverSocket.configureBlocking(false);// 创建多路复用器Selector selector = Selector.open();// 注册serversocket到selector, 关注连接事件serverSocket.register(selector, SelectionKey.OP_ACCEPT);System.out.println("服务启动成功");while (true) {// 阻塞等待需要处理的事件selector.select();Set<SelectionKey> selectionKeys = selector.selectedKeys();Iterator<SelectionKey> iterator = selectionKeys.iterator();while (iterator.hasNext()) {SelectionKey key = iterator.next();// 如果是连接事件  > 获取连接并且注册读事件if (key.isAcceptable()) {ServerSocketChannel server = (ServerSocketChannel) key.channel();SocketChannel socketChannel = server.accept();socketChannel.configureBlocking(false);socketChannel.register(selector, SelectionKey.OP_READ);System.out.println("客户端连接成功");} else if (key.isReadable()) {SocketChannel socketChannel = (SocketChannel) key.channel();ByteBuffer byteBuffer = ByteBuffer.allocate(128);int len = socketChannel.read(byteBuffer);if (len > 0) {System.out.println("接收到消息:" + new String(byteBuffer.array()));} else {System.out.println("客户端断开连接");socketChannel.close();}}// 从事件集合里删除本次处理的key,防止下次select重复处理iterator.remove();}}}
}

NIO的三大核心组件:

  1. channel 类似于流,每个 channel 对应一个 buffer缓冲区,buffer 底层就是个数组
  2. channel 会注册到 selector 上,由 selector 根据 channel 读写事件的发生将其交由某个空闲的线程处理
  3. NIO 的 Buffer 和 channel 都是既可以读也可以写

常见问题

为什么Netty使用NIO而不是AIO?        

        在Linux系统上,AIO的底层实现仍使用Epoll,没有很好实现AIO,因此在性能上没有明显的优势,而且被JDK封装了一层,不容易深度优化,Linux上AIO还不够成熟。Netty是异步非阻塞框架,Netty在NIO上做了很多异步的封装。 

相关文章:

BIO和NIO编程(待完善)

目录 IO模型 BIO NIO 常见问题 IO模型 Java共支持3种网络编程IO模式&#xff1a;BIO&#xff0c;NIO&#xff0c;AIO BIO 同步阻塞模型&#xff0c;一个客户端连接对应一个处理线程 代码示例&#xff1a; Server端&#xff1a; public class BioServer {private static …...

基于RocketMQ实现分布式事务

前言 在上一篇文章Spring Boot自动装配原理以及实践我们完成了服务通用日志监控组件的开发&#xff0c;确保每个服务都可以基于一个注解实现业务功能的监控。 而本文我们尝试基于RocketMQ实现下单的分布式的事务。可能会有读者会有疑问&#xff0c;之前我们不是基于Seata完成了…...

TikTok社会学:短视频如何塑造社会认知?

TikTok&#xff0c;作为一款全球性的短视频平台&#xff0c;正在深刻地影响着用户的社会认知。在这个数字时代&#xff0c;短视频不仅仅是娱乐的载体&#xff0c;更是塑造和反映社会认知的一面镜子。本文将深入探讨TikTok是如何通过短视频影响社会认知&#xff0c;以及这种影响…...

小秋SLAM入门实战深度学习所有文章汇总

如何用python代码实现虚拟拖拽 MediaPipe Losses 损失函数 深度学习激活函数Activation Functions 【深度学习Regularization正则化】 深度学习: 数据扩充 (Data Augmentation) 【keras-yolo3】 【YOLO源码解读】 caffe源码解读系列 Python中的异常处理 精确率、精度&#xff…...

linux搭建git仓库

git安装与配置 # git安装 yum install -y git# git配置(以下为root用户下配置) # 添加git组 groupadd git# 添加账号、密码(账号zdtest可根据自己需求修改) useradd zdtest -g git passwd zdtest创建远程仓库(linux端) 创建个人文件夹 mkdir -p /home/data/zdtestcd /home/d…...

19. Mysql 循环语句

文章目录 概念循环语句while 循环语句repeat 循环语句loop 循环语句iterate 和 leave 语句 精选示例总结参考资料 概念 循环结构是编程中常见的控制结构&#xff0c;它允许我们重复执行一段代码&#xff0c;直到满足特定条件为止。 在 Mysql 中&#xff0c;常用来实现各种复杂…...

【qt】解决qt里编辑qss后失效问题(qt编码问题)

1、先创建qss文本stylesheet.qss 以按钮为例 QPushButton {background-color:rgb(240,255,255);color: rgb(0, 0, 2);border-style: outset;border-color: beige;border-radius: 10px; }/* hover按钮悬浮&#xff0c;鼠标悬浮在按钮上的状态&#xff0c;按钮颜色 */QPushButto…...

MySQL数据库高级SQL语句及存储过程

目录 一、高级SQL语句 &#xff08;一&#xff09;case语句 1.语法定义 2.示例 &#xff08;二&#xff09;空值(NULL) 和 无值( ) 1.区别 2.示例 &#xff08;1&#xff09;字符长度 &#xff08;2&#xff09;判断方法 ① 空值(NULL) ② 无值( ) &#xff08;3…...

使用idea构建父子类springboot项目教程

第一步创建一个父类java项目&#xff08;最外层java项目&#xff09; 1.点击File 然后点击new 再点击Project 2.点击Maven 配置Java版本 再点击next 3.GroupId&#xff1a;包结构&#xff0c;ArtifactId&#xff1a;项目名称&#xff0c;填写完&#xff0c;点击next 4.点击…...

TCP_可靠数据传输原理

引言 在网络通信中&#xff0c;TCP是确保数据可靠传输的关键协议。但在我们深入研究TCP拥塞控制技术之前&#xff0c;让我们先探索可靠数据传输的原理&#xff0c;特别是TCP头部中一些重要字段的作用。 网络层提供了点对点的通信服务&#xff0c;努力交付数据报&#xff0c;但…...

Python随机点名

python随机点名 # 生成 0 ~ 9 之间的随机数 # 导入 random(随机数) 模块 import random print(random.randint(0,9)) 执行以上代码输出结果为: 4 尝试一下 以上实例我们使用了 random 模块的 randint() 函数来生成随机数&#xff0c;你每次执行后都返回不同的数字&a…...

HarmonyOS4.0系统性深入开发07创建一个ArkTS卡片

创建一个ArkTS卡片 在已有的应用工程中&#xff0c;创建ArkTS卡片&#xff0c;具体操作方式如下。 创建卡片。 根据实际业务场景&#xff0c;选择一个卡片模板。 在选择卡片的开发语言类型&#xff08;Language&#xff09;时&#xff0c;选择ArkTS选项&#xff0c;然后单…...

胡润研究院发布《2023胡润中国最具历史文化底蕴品牌榜》

胡润研究院发布《2023胡润中国最具历史文化底蕴品牌榜》&#xff0c;前十名分别是片仔癀、同仁堂、贵州茅台、五粮液、中国银行、中华、黄山、农业银行、建设银行、汾酒。 榜单调研范围涵盖中国内地具有60年以上历史的为消费者提供产品或服务的品牌&#xff0c;综合考察品牌历史…...

MFC编程技巧与范例详解01

目录 1、MFC概述 &#xff08;1&#xff09;、MFC为什么不用C语言使用C &#xff08;2&#xff09;、MFC的开发模型文档-视图模型 &#xff08;3&#xff09;、一个完善的MFC程序应该包括 &#xff08;4&#xff09;、MFC常用的类 2、MFC的特性 &#xff08;1&#xff09…...

TPS5430正负电源模块

TPS5430正负电源模块 Chapter1 TPS5430正负电源模块一、芯片重要参数二、tps5430参考电路讲解以及PCB布局1.正压降压&#xff08;15V转12V&#xff09;2.正压降负压&#xff08;15V转-12V&#xff09; Chapter2 使用tps5430制作正负DC-DC降压电源&#xff0c;tps7a47和tps7a33制…...

【LeetCode 面试经典150题】45. Jump Game II 跳跃游戏II

45. Jump Game II 题目大意 You are given a 0-indexed array of integers nums of length n. You are initially positioned at nums[0]. Each element nums[i] represents the maximum length of a forward jump from index i. In other words, if you are at nums[i], yo…...

RustDesk连接客户端提示key不匹配 Key Mismatch无法连接(已解决)

环境: RustDesk1.1.9 服务端docker部署 问题描述: RustDesk连接客户端提示key不匹配 Key Mismatch无法连接 解决方案: 1.docker部署RustDesk服务检查配置 networks:rustdesk-net:external: falsevolumes:hbbr:hbbs:services:hbbs:container_name: rustdesk-hbbsport…...

puppeteer入门指南

一、简介 Puppeteer 是一个 Node 库&#xff0c;它提供了一个高级 API 来通过 DevTools 协议控制 Chromium 或 Chrome。 二、使用 1、安装nodejs最新版 2、安装puppeteer-core npm install puppeteer-core 3、编写main.js const puppeteer require(puppeteer-core);(as…...

vue3按钮点击频率控制

现有一个按钮&#xff0c;如下图 点击时 再次点击 刷新窗口再次点击 刷新窗口依然可以实现点击频率控制。 代码实现&#xff1a; <template><!--<el-config-provider :locale"locale"><router-view/></el-config-provider>--><el…...

(一)Matlab数值计算基础

目录 1.2Matlab中的数据类型 1.2Matlab中的数据类型 逻辑型 逻辑型变量值为1或0字符型 MATLAB的字符型输入使用单引号括起来&#xff0c;字符串存储为字符数组&#xff0c;每个元素占一个ASCII字符数值型 数值型分为整型&#xff08;int&#xff09;、单精度浮点型&#xff0…...

智慧医疗能源事业线深度画像分析(上)

引言 医疗行业作为现代社会的关键基础设施,其能源消耗与环境影响正日益受到关注。随着全球"双碳"目标的推进和可持续发展理念的深入,智慧医疗能源事业线应运而生,致力于通过创新技术与管理方案,重构医疗领域的能源使用模式。这一事业线融合了能源管理、可持续发…...

React Native 导航系统实战(React Navigation)

导航系统实战&#xff08;React Navigation&#xff09; React Navigation 是 React Native 应用中最常用的导航库之一&#xff0c;它提供了多种导航模式&#xff0c;如堆栈导航&#xff08;Stack Navigator&#xff09;、标签导航&#xff08;Tab Navigator&#xff09;和抽屉…...

Nginx server_name 配置说明

Nginx 是一个高性能的反向代理和负载均衡服务器&#xff0c;其核心配置之一是 server 块中的 server_name 指令。server_name 决定了 Nginx 如何根据客户端请求的 Host 头匹配对应的虚拟主机&#xff08;Virtual Host&#xff09;。 1. 简介 Nginx 使用 server_name 指令来确定…...

相机从app启动流程

一、流程框架图 二、具体流程分析 1、得到cameralist和对应的静态信息 目录如下: 重点代码分析: 启动相机前,先要通过getCameraIdList获取camera的个数以及id,然后可以通过getCameraCharacteristics获取对应id camera的capabilities(静态信息)进行一些openCamera前的…...

MySQL 8.0 OCP 英文题库解析(十三)

Oracle 为庆祝 MySQL 30 周年&#xff0c;截止到 2025.07.31 之前。所有人均可以免费考取原价245美元的MySQL OCP 认证。 从今天开始&#xff0c;将英文题库免费公布出来&#xff0c;并进行解析&#xff0c;帮助大家在一个月之内轻松通过OCP认证。 本期公布试题111~120 试题1…...

数据库分批入库

今天在工作中&#xff0c;遇到一个问题&#xff0c;就是分批查询的时候&#xff0c;由于批次过大导致出现了一些问题&#xff0c;一下是问题描述和解决方案&#xff1a; 示例&#xff1a; // 假设已有数据列表 dataList 和 PreparedStatement pstmt int batchSize 1000; // …...

vue3+vite项目中使用.env文件环境变量方法

vue3vite项目中使用.env文件环境变量方法 .env文件作用命名规则常用的配置项示例使用方法注意事项在vite.config.js文件中读取环境变量方法 .env文件作用 .env 文件用于定义环境变量&#xff0c;这些变量可以在项目中通过 import.meta.env 进行访问。Vite 会自动加载这些环境变…...

学习STC51单片机32(芯片为STC89C52RCRC)OLED显示屏2

每日一言 今天的每一份坚持&#xff0c;都是在为未来积攒底气。 案例&#xff1a;OLED显示一个A 这边观察到一个点&#xff0c;怎么雪花了就是都是乱七八糟的占满了屏幕。。 解释 &#xff1a; 如果代码里信号切换太快&#xff08;比如 SDA 刚变&#xff0c;SCL 立刻变&#…...

RabbitMQ入门4.1.0版本(基于java、SpringBoot操作)

RabbitMQ 一、RabbitMQ概述 RabbitMQ RabbitMQ最初由LShift和CohesiveFT于2007年开发&#xff0c;后来由Pivotal Software Inc.&#xff08;现为VMware子公司&#xff09;接管。RabbitMQ 是一个开源的消息代理和队列服务器&#xff0c;用 Erlang 语言编写。广泛应用于各种分布…...

接口自动化测试:HttpRunner基础

相关文档 HttpRunner V3.x中文文档 HttpRunner 用户指南 使用HttpRunner 3.x实现接口自动化测试 HttpRunner介绍 HttpRunner 是一个开源的 API 测试工具&#xff0c;支持 HTTP(S)/HTTP2/WebSocket/RPC 等网络协议&#xff0c;涵盖接口测试、性能测试、数字体验监测等测试类型…...