1.netty介绍
1.介绍
- 是JBOSS通过的java开源框架
- 是异步的,基于事件驱动(点击一个按钮调用某个函数)的网络应用框架,高性能高可靠的网络IO程序
- 基于TCP,面向客户端高并发应用/点对点大量数据持续传输的应用
- 是NIO框架 (IO的一层层封装) TCP/IP->javaIO和网络编程–>NIO—>Netty
2.应用场景
- 互联网 RPC框架比如阿里的Dubbo
- 网络游戏 可以定制TCP/UDP 和http协议栈
- 大数据 hadoop序列化组件和实时数据文件共享 AVRO
还有Flink Spark Akka…其他开源项目
3.IO模型
- BIO(blocking原生javaIO,阻塞性,一个连接需要一个线程处理,连接不使用阻塞也占用线程)
//面试: 适用连接数目少架构稳定的,对服务器资源要求高,但程序简单容易理解 jdk1.4之前唯一的选择- NIO(No blocking/new 同步非阻塞)(一个线程使用selector维护多个客户端,轮询检测活动 多路复用,可以开多个线程) 图1nettyNIO原理、
//适用 连接数目多且连接比较短的(轻操作)的结果 比如聊天,弹幕,服务器之间通信,编程复杂 jdk1.4开始支持
3. AIO(等待时间长才需要异步,异步非阻塞) 是有效请求才启动线程
//面试: 适合;连接数量多且连接长的, 比如相册服务器.编程复杂,jdk7开始支持
4.BIO实例(可以使用线程池改善)
win的 telnet 127.0.0.1 6666端口的ctrl+]的send xxx可以发送数据到服务器
5.NIO
- 结构 如果通道没有事件,选择器不处理,线程也不阻塞 selector(选择器)<–>channel(通道)<—> buffer(缓冲区,数据先在这里实现了非阻塞)<—>socket //IntBuffer的使用
java除了boolean类型,是类型统一管理,所以比BIO更快 //!!!一定要flip()读写切换 才能读取值- 关系
1.buffer是内存块(面向缓冲/块的编程),是一个数组,达到一定量才给channel
2.selector由哪个channel有事件才切换过去的,不是自动切换的 ?
3.buffer channel是双向的,区别BIO 有in output流
4.一个thread对应一个selector,对应多个channel
6.Buffer的属性
position
filp()会使他变为0,读写的时候也会改变,一直往后移
limit(块的最大容量) 和capacity(自己设置的块容量)一样用来判断是否超出范围 capacity 自己设置的数组容量 mark 标记
//常用的api
IntBuffer in=IntBuffer.allocate(5);//5个容量 .flip //读写切换,如果是读的可以切换为写的,所以说NIO是双向的.position(1);//设置读写的位置.limit(3);//设置读写限制个数<3.get(); //得到元素通过iterator.put(1);.put(1,1);//在指定位置放数据.clear();//清除缓冲器 .hasRemain();//相当于hasNext().isReadOnly();//是否为只读缓冲区//抽象方法jdk1.6引入 hasArray()缓冲区是否可访问底层的buffer数组 array()返回buffer数组//常用ByteBuffer
7.Channel 可以向buffer读写和拷贝
1.ServerSockerChannel 类似ServerSocker,SockerChannel就是Socket,还有一模一样的UDP的类
2.FileChannel类read() 通道读数据到buffer write() buffer写入通道 transferFrom()目标通道复制到本通道 transferTo() channel复制到目标通道
8.使用channel生成文件,与BIO的关系,底层就是BIO
String str="aaa";out=new FileOutputStream("d;\\aaa.txt"); //输出流包括channelFileChannel channel=out.getChannel();byteBuffer=ByteBuffer.allocate(1024);byteBuffer.put(str.getBytes);byteBuffer.flip(); //初始状态是读,切换成写channel.write(byteBuffer);//向其他通道写out.close();//关闭流
public class bufferDemo {public static void main(String[] args) throws IOException {String str="helloworld";FileOutputStream out = new FileOutputStream("D:\\abs.txt");FileChannel channel = out.getChannel();ByteBuffer byteBuffer=ByteBuffer.allocate(1024);byteBuffer.position(2);byteBuffer.put(str.getBytes()); //放在limit后面会报错,这个是限制容量//相当于截断写入的数据byteBuffer.limit(7);//必须要写byteBuffer.flip();channel.write(byteBuffer);channel.close();out.close();}
}
9.读数据
File file=new File("d:\\aa.txt");in=new FileInputStream(file);fileChannel=in.getChannel();byteBuffer= ByteBuffer.allocate((int)file.length());fileChannel.read(byteBuffer);sout(new String( byteBuffer.array()));in.close();
public class bfDemo {public static void main(String[] args) throws IOException {File file = new File("D:\\abs.txt");FileInputStream inputStream = new FileInputStream(file);FileChannel channel = inputStream.getChannel();ByteBuffer byteBuffer = ByteBuffer.allocate((int) file.length());channel.read(byteBuffer);System.out.println(new java.lang.String(byteBuffer.array()));}
}
10.一个buffer 多个channel(创建两个流)拷贝文件 边读边写
//在java写路径相对位置是 本项目最父类的项目路径!!!(以前写相对路径总是出错)
//必须需要不然position=limit
byteBytebuffer.clear();.flip();public class bfDemo3Copy {public static void main(String[] args) throws IOException {FileInputStream inputStream = new FileInputStream("D:\\abs.txt");FileChannel c1 = inputStream.getChannel();FileOutputStream fileOutputStream = new FileOutputStream("D:\\abs1.txt");FileChannel c2 = fileOutputStream.getChannel();ByteBuffer allocate = ByteBuffer.allocate(inputStream.available());c1.read(allocate);allocate.flip();c2.write(allocate);}}
//一块一块读,反转写入.steps are combinate bytes to buffer and send to another channel(outputStream)
public class NIOFileChannel03 {public static void main(String[] args) throws Exception {FileInputStream fileInputStream = new FileInputStream("1.txt");FileChannel fileChannel01 = fileInputStream.getChannel();FileOutputStream fileOutputStream = new FileOutputStream("2.txt");FileChannel fileChannel02 = fileOutputStream.getChannel();ByteBuffer byteBuffer = ByteBuffer.allocate(512);while (true) { //循环读取byteBuffer.clear(); //清空buffer!!!int read = fileChannel01.read(byteBuffer);System.out.println("read =" + read);if(read == -1) { //表示读完break;}//将buffer 中的数据写入到 fileChannel02 -- 2.txtbyteBuffer.flip();fileChannel02.write(byteBuffer);}//关闭相关的流fileInputStream.close();fileOutputStream.close();}
}
11.拷贝图片
destch.transferFrom(sourceCh,0,sourceCh.size());//关闭所有通道和流
public class bfDemo4transferCopy {public static void main(String[] args) throws IOException {FileInputStream inputStream = new FileInputStream("D:\\abs.txt");FileChannel c1 = inputStream.getChannel();FileOutputStream fileOutputStream = new FileOutputStream("D:\\abs3.txt");FileChannel c2 = fileOutputStream.getChannel();c2.transferFrom(c1,0,c1.size());}
}
12.buffer放的顺序和取的顺序一样不然抛出异常BufferUnderflowException
ByteBuffer bf= ByteBuffer.allocate(64);bf.putInt(100); bf.putLong(100L);bf.flip();bf.getInt(); bf.getLong();
13.写完转为只读buffer
//12的代码
buffer.asReadOnlyBuffer();public class OnlyWrite {public static void main(String[] args) {ByteBuffer bf= ByteBuffer.allocate(64);bf.putInt(100);bf.putLong(100L);bf.flip();ByteBuffer byteBuffer = bf.asReadOnlyBuffer();byteBuffer.getInt();byteBuffer.getLong();byteBuffer.putLong(10);//错误不能写,只能读}
}
14.MappedByteBuffer可以在堆外内存修改文件(效率高)操作系统不用拷贝一次到内存
access=new RandAccessFile("1.txt","rw");channel=access.getChannel();
map=channel.map(FileChannel.MapMode.READ_WRITE,0,5);模式,开始位置,结束位置 <5bytemap.put(0,(byte)'H'); //在内存直接修改文件内容,然后放回磁盘access.close();
public class MapBuffer {public static void main(String[] args) throws IOException {RandomAccessFile access = new RandomAccessFile("1.txt", "rw");FileChannel channel = access.getChannel();//到内存修改的大小范围是 0-5, if out of the bound will throw an expectionMappedByteBuffer map = channel.map(FileChannel.MapMode.READ_WRITE, 0, 5);map.put(0,(byte)'A');map.put(4,(byte)'H');access.close();System.out.println("修改成功");}
}
//idea需要在文件夹外打开,不然看不到效果
15.分散和聚集 scatter(写的时候放到多个buffer[数组array])和gather(读的时候多个buffer) 加快读写效率(the key is using many buffer to read and read)(read and write only once that can get more buffer)
public class scatterAndGather {public static void main(String[] args) throws IOException {ServerSocketChannel serverSocket = ServerSocketChannel.open().bind(new InetSocketAddress(6666));ByteBuffer[] byteBuffers= new ByteBuffer[2];byteBuffers[0]=ByteBuffer.allocate(3);byteBuffers[1]=ByteBuffer.allocate(5);SocketChannel accept = serverSocket.accept();int msgLen=8;while (true){int byteRead=0;while (byteRead<msgLen){long read = accept.read(byteBuffers);byteRead++;System.out.println("bufferRead:"+byteRead);Arrays.asList(byteBuffers).stream().map(buffer->"position"+buffer.position()+",limit="+buffer.limit()).forEach(System.out::println);}Arrays.asList(byteBuffers).stream().forEach(buffer ->buffer.flip() );long byteWrite=0;while (byteWrite<msgLen){//一次读出多少个字节long l=accept.write(byteBuffers);byteWrite+=l;System.out.println(byteWrite);}Arrays.asList(byteBuffers).forEach(byteBuffer -> {System.out.println(new String(byteBuffer.array() ));byteBuffer.clear();});System.out.println("byteRead:="+byteRead+"byteWrite:"+byteWrite+"msgLen:"+msgLen);}}
}
16.selector管理多个连接(channel) 不停如轮询检测事件,有事件处理,阻塞不等待,处理其他通道的请求,解决了多线程单通道的问题,提高了性能
selector类selects()//得到channel的连接的selectkey集合阻塞,selector.select(1000)//阻塞1000毫秒,必须返回数据selector.wakeup()//唤醒selector,阻塞中可以唤醒selector.selectNow()//非阻塞,立即返回结果,核心方法selector.selectedKeys() //select获取绑定channel产生事件的selectkey集合
//可以注册channel到selector上返回selectionKey (集合)
相关文章:
1.netty介绍
1.介绍 是JBOSS通过的java开源框架是异步的,基于事件驱动(点击一个按钮调用某个函数)的网络应用框架,高性能高可靠的网络IO程序基于TCP,面向客户端高并发应用/点对点大量数据持续传输的应用是NIO框架 (IO的一层层封装) TCP/IP->javaIO和网络编程–>NIO—>Netty 2.应用…...
【Jmeter】压测mysql数据库中间件mycat
目录 背景 环境准备 1、下载Jmeter 2、下载mysql数据库的驱动包 3、要进行测试的数据库 Jmeter配置 1、启动Jmeter图形界面 2、加载mysql驱动包 3、新建一个线程组,然后如下图所示添加 JDBC Connection Configuration 4、配置JDBC Connection Configurati…...
leetcode原题 路径总和 I II III(递归实现)
路径总和 I : 给你二叉树的根节点 root 和一个表示目标和的整数 targetSum 。判断该树中是否存在 根节点到叶子节点 的路径,这条路径上所有节点值相加等于目标和 targetSum 。如果存在,返回 true ;否则,返回 false 。…...
【css】css设置表格样式-边框线合并
<style> table, td, th {border: 1px solid black;//设置边框线 }table {width: 100%; }td {text-align: center;//设置文本居中 } </style> </head> <body><table><tr><th>Firstname</th><th>Lastname</th><t…...
使用Flutter的image_picker插件实现设备的相册的访问和拍照
文章目录 需求描述Flutter插件image_picker的介绍使用步骤1、添加依赖2、导入 例子完整的代码效果 总结 需求描述 在应用开发时,我们有很多场景要使用到更换图片的功能,即将原本的图像替换设置成其他的图像,从设备的相册或相机中选择图片或拍…...
数学建模体系
1评价类 主观求权重:层次分析法客观求权重:TOPSIS综合评价:典型相关分析 2预测插值算法拟合多元回归分析时间序列分析、ARCH和garch模型岭回归和lasso回归 3关系相关系数典型相关分析多元回归分析灰色关联分析 4图最短路径:迪杰斯…...
13.7 CentOS 7 环境下大量创建帐号的方法
13.7.1 一些帐号相关的检查工具 pwck pwck 这个指令在检查 /etc/passwd 这个帐号配置文件内的信息,与实际的主文件夹是否存在等信息, 还可以比对 /etc/passwd /etc/shadow 的信息是否一致,另外,如果 /etc/passwd 内的数据字段错…...
HTML5 Canvas(画布)
<canvas>标签定义图形,比如图表和其他图像,你必须用脚本来绘制图形。 在画布上( Canvas )画一个共红色矩形,渐变矩形,彩色矩形,和一些彩色文字。 什么是 Canvas? HTML5<c…...
io的异常处理以及properties
try(流对象的创建) { 对象的处理逻辑} catch(IOException e) { 异常的处理逻辑} public static void test4(){try(FileWriter fwnew FileWriter("a.txt",true); ){char[] cbuf{a};//写入一个字符串组fw.write(cbuf);}catch(IOException e){e.printStackTrace();}}上面…...
Linux下基于Dockerfile构建镜像应用(1)
目录 基于已有容器创建镜像 Dockerfile构建SSHD镜像 构建镜像 测试容器 可以登陆 Dockerfile构建httpd镜像 构建镜像 测试容器 Dockerfile构建nginx镜像 构建镜像 概述: Docker 镜像是Docker容器技术中的核心,也是应用打包构建发布的标准格式。…...
JS中常见的模块管理规范梳理
一、CommonJS规范 CommonJS规范是一种用于JavaScript模块化开发的规范,它定义了模块的导入、导出方式和加载机制,主要用在Node开发中。 1. 使用场景 服务器端开发:Node.js是使用CommonJS规范的,因此在服务器端开发中࿰…...
3维空间下按平面和圆柱面上排版设计
AR空间中将若干平面窗口排列在指定平面或圆柱体面上 平面排版思路 指定平面方向向量layout_centre ,平面上的一点作为排版版面的中心layout_position float3 layout_position = float3(0,0,-10); float3 layout_centre = float3(0,0,1...
【Spring框架】Spring AOP
目录 什么是AOP?AOP组成Spring AOP 实现步骤Spring AOP实现原理JDK Proxy VS CGLIB 什么是AOP? AOP(Aspect Oriented Programming):⾯向切⾯编程,它是⼀种思想,它是对某⼀类事情的集中处理。⽐如…...
寻找旋转排序数组中的最小值——力扣153
文章目录 题目描述解法 二分法 题目描述 解法 二分法 int findMin(vector<int>& nums){int l0, rnums.size()-1;while(l<r){int mid (lr)/2;if(nums[mid]<nums[r]) rmid;else lmid1;}return nums[l];}...
安卓逆向 - 基础入门教程
一、引言 1、我们在采集app数据时,有些字段是加密的,如某麦网x-mini-wua x-sgext x-sign x-umt x-utdid等参数,这时候我们需要去分析加密字段的生成。本篇将以采集的角度讲解入门安卓逆向需要掌握的技能、工具。 2、安卓(Androi…...
验证码安全志:AIGC+集成环境信息信息检测
目录 知己知彼,黑灰产破解验证码的过程 AIGC加持,防范黑灰产的破解 魔高一丈,黑灰产AIGC突破常规验证码 双重防护,保障验证码安全 黑灰产经常采用批量撞库方式登录用户账号,然后进行违法违规操作。 黑灰产将各种方…...
R-Meta分析教程
详情点击链接:R-Meta模型教程 一:Meta分析的选题与文献计量分析CiteSpace应用 1、Meta分析的选题与文献检索 1)什么是Meta分析? 2)Meta分析的选题策略 3)文献检索数据库 4)精确检索策略,如何检索全、检索准 5)文献的管理与…...
【3维视觉】3D空间常用算法(点到直线距离、面法线、二面角)
3D空间点到直线的距离 3D空间点到直线的距离 3D空间的曲率 三维空间有三个基本元素,点,线,面。那么曲率是如何定义的呢? 点的曲率? 线的曲率? 面的曲率? 法曲率 设曲面上的曲线在某一点处的切…...
Nodejs 第四章(Npm install 原理)
在执行npm install 的时候发生了什么? 首先安装的依赖都会存放在根目录的node_modules,默认采用扁平化的方式安装,并且排序规则.bin第一个然后系列,再然后按照首字母排序abcd等,并且使用的算法是广度优先遍历,在遍历依…...
[深度学习] GPU处理能力(TFLOPS/TOPS)
计算能力换算 理论峰值 = GPU芯片数量GPU Boost主频核心数量*单个时钟周期内能处理的浮点计算次数 只不过在GPU里单精度和双精度的浮点计算能力需要分开计算,以最新的Tesla P100为例: 双精度理论峰值 = FP64 Cores *…...
UE5 学习系列(二)用户操作界面及介绍
这篇博客是 UE5 学习系列博客的第二篇,在第一篇的基础上展开这篇内容。博客参考的 B 站视频资料和第一篇的链接如下: 【Note】:如果你已经完成安装等操作,可以只执行第一篇博客中 2. 新建一个空白游戏项目 章节操作,重…...
龙虎榜——20250610
上证指数放量收阴线,个股多数下跌,盘中受消息影响大幅波动。 深证指数放量收阴线形成顶分型,指数短线有调整的需求,大概需要一两天。 2025年6月10日龙虎榜行业方向分析 1. 金融科技 代表标的:御银股份、雄帝科技 驱动…...
JavaSec-RCE
简介 RCE(Remote Code Execution),可以分为:命令注入(Command Injection)、代码注入(Code Injection) 代码注入 1.漏洞场景:Groovy代码注入 Groovy是一种基于JVM的动态语言,语法简洁,支持闭包、动态类型和Java互操作性,…...
ES6从入门到精通:前言
ES6简介 ES6(ECMAScript 2015)是JavaScript语言的重大更新,引入了许多新特性,包括语法糖、新数据类型、模块化支持等,显著提升了开发效率和代码可维护性。 核心知识点概览 变量声明 let 和 const 取代 var…...
【OSG学习笔记】Day 18: 碰撞检测与物理交互
物理引擎(Physics Engine) 物理引擎 是一种通过计算机模拟物理规律(如力学、碰撞、重力、流体动力学等)的软件工具或库。 它的核心目标是在虚拟环境中逼真地模拟物体的运动和交互,广泛应用于 游戏开发、动画制作、虚…...
前端倒计时误差!
提示:记录工作中遇到的需求及解决办法 文章目录 前言一、误差从何而来?二、五大解决方案1. 动态校准法(基础版)2. Web Worker 计时3. 服务器时间同步4. Performance API 高精度计时5. 页面可见性API优化三、生产环境最佳实践四、终极解决方案架构前言 前几天听说公司某个项…...
关于iview组件中使用 table , 绑定序号分页后序号从1开始的解决方案
问题描述:iview使用table 中type: "index",分页之后 ,索引还是从1开始,试过绑定后台返回数据的id, 这种方法可行,就是后台返回数据的每个页面id都不完全是按照从1开始的升序,因此百度了下,找到了…...
HTML 列表、表格、表单
1 列表标签 作用:布局内容排列整齐的区域 列表分类:无序列表、有序列表、定义列表。 例如: 1.1 无序列表 标签:ul 嵌套 li,ul是无序列表,li是列表条目。 注意事项: ul 标签里面只能包裹 li…...
DIY|Mac 搭建 ESP-IDF 开发环境及编译小智 AI
前一阵子在百度 AI 开发者大会上,看到基于小智 AI DIY 玩具的演示,感觉有点意思,想着自己也来试试。 如果只是想烧录现成的固件,乐鑫官方除了提供了 Windows 版本的 Flash 下载工具 之外,还提供了基于网页版的 ESP LA…...
unix/linux,sudo,其发展历程详细时间线、由来、历史背景
sudo 的诞生和演化,本身就是一部 Unix/Linux 系统管理哲学变迁的微缩史。来,让我们拨开时间的迷雾,一同探寻 sudo 那波澜壮阔(也颇为实用主义)的发展历程。 历史背景:su的时代与困境 ( 20 世纪 70 年代 - 80 年代初) 在 sudo 出现之前,Unix 系统管理员和需要特权操作的…...
