远程通信及AIO、BIO、NIO初级讲解
分布式架构网络通信
基本原理
将流从一台计算机传递到另外一台计算机,基于传输协议和网络IO实现。
网络数据传输的要素:
协议:
- UDP:广播协议,面向无连接,速度快,不安全
- TCP:面向连接协议,速度不快,较为安全
RPC
remote procedure call,远程服务调用
解决本地调用远程服务像调用本地自己服务一样。
其中包含四个组件:
- 客户端(client),服务调用方。
- 客户端存根(Client Stub),存放服务端的地址消息,再将客户端的请求参数打包成网络消息,然后通过网络远程发送给服务方。
- 服务端(Server),真正的服务提供者。
- 服务端存根(Server Stub),接收客户端发送过来的消息,将消息解包,并调用本地的方法。
无论是何种类型的数据,最终都需要转换二进制流再网络上进行传输,数据的发送方需要将对象转换为二进制流,而数据的接收方则需要把二进制流转再恢复为对象。
RMI
RMI指的远程方法调用,java原生实现的远程通信。也就是一台机器的对象调用另一个虚拟机上的方法对象。
RMI组件:
- 客户端:
- 存根/桩(Stub):远程对象在客户端上的代理;(本地保存远程代理对象)
- 远程引用层(Remote Reference Layer):解析并执行远程引用协议
- 传输层(Transport):发送调用、传递远程方法参数、接收远程方法执行结果
- 服务端:
- 骨架(Skeleton):读取客户端传递的方法参数,调用服务器方的事及对象方法,并接收方法执行后的返回值;
- 远程引用层(Remote Reference Layer):处理远程引用后向股价发送远程方法调用;
- 传输层(Transport):监听客户端的入站连接,接收并转发调用到远程引用层。
- 注册表(Registry):以URL形式注册远程对象,并向客户端回复对远程对象的引用。
BIO、NIO、AIO
BIO:同步阻塞IO
- serverSocket.accept(); //同步阻塞
- 每次服务端只能接收并处理一个请求,处理完毕才会执行第二个,并且在不传数据的时候就会一直阻塞,浪费服务器资源。延申出用线程处理,但同样会出现c10k问题(c10k问题 即Client发送上万的请求到服务器)。当然有人会想到线程池,线程池设置最大线程数是500,则就是500,再多的请求也只有等待甚至超时。
NIO:同步非阻塞IO(new io),由操作系统内部实现,底层调用了linux内核的accept函数
一个请求一个通道。客户端发送的连接请求都会被注册到多路复用器上,多路复用器轮询到连接有IO请求时(读写)才启动一个线程进行处理。
- 通道(Channels):
Channel数据连接的通道。数据可以从Channel读到Buffer中,也可以从Buffer写道Channel中。
- 缓冲区(Buffers):
通道channel可以向缓冲区Buffer中写数据,也可以像buffer中存数据。
- 选择器(Selector):
主线程创建一个Selector使用选择器,借助单一线程,可对数量庞大的活动I/O通道实现监控和维护。
accept:可以连接
read:
write:
//nio的创建主要方法解析 //开启服务通道 ServerSocketChannel.open(); //注册,标记服务连接状态为ACCEPT状态 serverSocketChannel.register(this.selector,SelectionKey.OP_ACCEPT); //当有至少一个通道被选中,执行此方法 this.selector.select(); /** * nio中以上三个方法调最后都调用了native方法,也就是调用了c中 * 方法,按顺序分别是 * epoll_create 创建epoll对象 * epoll_ctl 将有事件的channel放到一个事件的集合中 * epoll_wait 返回就绪事件 **/
AIO:异步非阻塞IO
aio只需要一个链接注册读写事件和回调方法。只需要调用API的read和write方法,并且方法都是异步的。
使用场景:链接数目多且比较长的架构,比如相册服务器,重点调用了OS参与并发操作,java7才开始支持的。
再了解同步和异步之前,先了解一下操作系统://进程资源分配的基本单位(静态)//线程是执行调度的基本单位(动态)操作系统是控制cpu执行哪些线程(也称线程调度器)CPU组成:(cpu里面有多核,每个核都有自己的寄存器和pc)1.Registers(寄存器):执行指令的数据(计算器组)2.PC(Program Counter):程序计数器,操控指令3.ALU(Arithmetic Logic Unit):运算单元,cpu调用ALU()执行算术与逻辑操作,数据反倒寄存器后使用alu来计算,然后再学会到寄存器,然后再由寄存器放到内存。//比如:2+3这条在内存上的指令 首先pc指向2+3这条指令 然后2和3会放到寄存器里面 然后alu会进行计算然后把计算结果放回到寄存器里面 然后寄存器写回到内存里面4.chache计算逻辑单元(intel中有MESICache)//经常写与经常读的数据单独存与缓存行中可以提高速度。客户端和服务端是如何进行通信的:通过操作系统的中断程序:每次客户端发动的请求道服务端,网口会有所感应,然后操作系统就会通过中断程序响应收发数据操作(操作系统做的),会找到是哪个客户端发的数据,就知道哪个channel发过来的数据,调用channel系统函数将事件放到就绪事件列表。这些都是操作系统做的。
同步和异步是指应用程序和内核的交互。(内核是操作系统)
- 同步:指用户进程触发IO操作等待或者轮询的方式查看IO操作是否就绪
- 异步:异步进程调用发出之后,调用者不会立刻得到结果。而是在调用发出之后,被调用者通过状态、通知来通知调用者,或者通过回调函数来处理这个调用。
同步IO是java自己处理IO读写
异步IO是java将IO读写委托给OS处理,需要将缓冲区的地址和大小传递给OS, OS 需要支持异步IO操作API
阻塞和非阻塞:
- 阻塞:排队取钱
- 非阻塞:排号不用排队取钱。
同步和异步关注的是消息通信机制
阻塞和非阻塞关注的是程序在等待调用结果(消息,返回值)时的状态
Netty
Netty是由JBOSS提供一个异步的基于事键驱动的网络变成框架。其中BossGroup负责接收用户连接,WorkGroup负责处理用户的io读写操作
Netty核心组件:
ChannelHandler接口定义了许多事件处理的方法,可以通过重写这些方法去实现具体的业务逻辑。可以实现该接口或者继承子类ChannelInboundHandlerAdapter。
需要重写的方法:
ChannelPipeline可以看出那个是多个ChannelHandler的集合,
ChannelHandlerContext,事件处理器上下文对象,Pipeline链中的实际处理节点。该对象中绑定了对应的Pipeline和Channel的信息。
ChannelFuture:异步的进行IO操作
EventLoop:为了更好的利用多核CPU资源。
ServerBootStrap:服务启动助手
Netty简单实现:
服务端:
创建2个线程池对象
- BossGroup线程池:负责接收
- WorkGroup线程池:负责读写
创建启动引导类
设置启动引导类
- 将两个线程池添加到组中,第一个线程池是负责接收,第二个线程池负责读写
- 然后给当前引导类设置通道类型
- 然后再设置绑定一个初始化监听ChannelInitialezer
- 事件监听Channel通道
- 获取pipeLine
- 绑定编码(encoder、decoder)
- 绑定我们的业务逻辑
- 获取入展信息,打印客户端传递的数据
- 事件监听Channel通道
启动引导类绑定端口
关闭通道
客户端:
- 创建连接池对象
- 创建客户端启动引导类BootStrap
- 配置启动引导类
- 设置通道NIO
- 设置Channel初始化监听
- 设置编码
- 使用启动引导类链接服务器,获取一个channel
- 循环写数据给服务器
远程调用有两种形式:
- 基于Http的restful形式的广义远程调用,springcould的feign和restemplate为代表,采用Http七层协议调用,协议的参数和相应序列化基本以JSON格式和XML格式为主
- 基于TCP的协议的RPC远程调用,以阿里的Dubbo为代表,主要通过netty来实现4层网络协议,NIO来异步传输,序列化可以是JSON或者hessian2以及java自带的序列化等,可以配置。
远程通信及AIO、BIO、NIO初级讲解相关推荐
- AIO+BIO+NIO+同步+异步+阻塞+非阻塞
一句话: AIO是NIO的升级版,NIO是BIO的升级版[1] 所以其实是用AIO IO名称 JDK版本 数据类型 IO类型 IO 流 BIO(偶尔也叫做OIO) <1.4 同步阻塞 ...
- AIO,BIO,NIO详解
一.基本概念 IO:阻塞IO BIO:同步阻塞IO.服务器实现模式为一个连接一个线程,即客户端有连接请求时服务器需要启动一个线程进行处理,如果这个链接不做任何事情会造成不必要的线程开销,当然可以通过线 ...
- Netty入门之BIO,NIO和AIO编程
Netty简介 Netty 的介绍 Netty 是由 JBOSS 提供的一个 Java 开源框架,现为 Github 上的独立项目. Netty 是一个异步的.基于事件驱动的网络应用框架,用以快速开发 ...
- 关于BIO | NIO | AIO的讨论
关于BIO | NIO | AIO的讨论一直存在,有时候也很容易让人混淆,就我的理解,给出一个解释: BIO | NIO | AIO,本身的描述都是在Java语言的基础上的.而描述IO,我们需要从两个 ...
- Netty序章之BIO NIO AIO演变
Netty序章之BIO NIO AIO演变 Netty是一个提供异步事件驱动的网络应用框架,用以快速开发高性能.高可靠的网络服务器和客户端程序.Netty简化了网络程序的开发,是很多框架和公司都在使用 ...
- Java之IO,BIO,NIO,AIO
2019独角兽企业重金招聘Python工程师标准>>> 参考文献一 IO基础知识回顾 java的核心库java.io提供了全面的IO接口.包括:文件读写.标准设备输出等.Java中I ...
- 【面试】迄今为止把同步/异步/阻塞/非阻塞/BIO/NIO/AIO讲的这么清楚的好文章(快快珍藏)...
网上有很多讲同步/异步/阻塞/非阻塞/BIO/NIO/AIO的文章,但是都没有达到我的心里预期,于是自己写一篇出来. 常规的误区 假设有一个展示用户详情的需求,分两步,先调用一个HTTP接口拿到详情数 ...
- 也谈BIO | NIO | AIO (Java版--转)
http://my.oschina.net/bluesky0leon/blog/132361 关于BIO | NIO | AIO的讨论一直存在,有时候也很容易让人混淆,就我的理解,给出一个解释: BI ...
- 迄今为止把同步/异步/阻塞/非阻塞/BIO/NIO/AIO讲的这么清楚的好文章
来源:编程新说 网上有很多讲同步/异步/阻塞/非阻塞/BIO/NIO/AIO的文章,但是都没有达到我的心里预期,于是自己写一篇出来. 常规的误区 假设有一个展示用户详情的需求,分两步,先调用一个HTT ...
最新文章
- 翻译Raywenderlich 最新文章What’s New in Swift 4
- dubbo-go v3 版本 go module 踩坑记
- [Ubuntu软件]好用轻巧的录屏软件——Kazam
- 康宁玻璃ct值计算公式_【钦州】CT室铅板生产厂家
- AndroidStudio_解决butterknife在module中使用BindView Attribute value must be constant---Android原生开发工作笔记229
- opencv 修改图像数值_【1】Introduction to OpenCV (2)使用VS生成OpenCV应用程序
- SAP License:欧洲人的项目
- 什么是dispatchEvent?
- 【应用统计学】简单随机抽样的区间估计和样本容量的确定
- strack.js调摄像头人脸识别拍照
- Python os.symlink创建软链接
- 基于android的手机掌上购物
- mc服务器常用指令_mc服务器新手指令
- SiamFC++ SiamCAR SiamBAN
- 微型计算机硬件系统中PROM是,1微型计算机硬件系统中最核心的部件是CPU.doc
- mysql用sql新增字段
- 生日悖论分析python_Python关于生日悖论分析
- 台式计算机硬盘英寸,浅谈3.5英寸硬盘与2.5英寸硬盘的区别
- RTT WK2412 spi-uart
- Java中什么时候用接口,什么时候用抽象类
热门文章
- 【S2VD】S2VD半监督视频降雨方法(Semi-Supervised Video Deraining with Dynamical Rain Generator)论文学习
- Python登录微信公众平台
- 2019年下半年教师资格幼儿园《保教知识与能力》真题与参考答案
- 计算机的英语作文模板,高中英语作文模板 第243期:My Computer 我的电脑
- loadrunner入门教程(17) --关联
- 输出一个贷款的迁徙率计算的代码
- 网络服务器 用到的技术
- yaml语法格式,springboot中yaml的使用
- 写代码没意思,来个程序媛鼓励师吧
- iOS原生二维码扫描(一)