2、nio的例子实践
下面的例子,说明了,nio中的三大核心类的基本使用。buffer,channel,selector
package com.shengsiyuan.nio; import org.junit.Test; import java.io.*;
import java.net.*;
import java.nio.ByteBuffer;
import java.nio.IntBuffer;
import java.nio.MappedByteBuffer;
import java.nio.channels.*;
import java.nio.channels.spi.SelectorProvider;
import java.security.SecureRandom;
import java.util.Arrays;
import java.util.Iterator;
import java.util.Set; public class NioTest1 { public static void main(String[] args) {
IntBuffer intBuffer = IntBuffer.allocate(10); for (int i = 0; i < intBuffer.capacity(); i++) {
int randomNumber = new SecureRandom().nextInt(20);
intBuffer.put(randomNumber);
} intBuffer.flip();//翻转,从写转到读状态 while (intBuffer.hasRemaining()) {
System.out.println(intBuffer.get());
} } public void testBuffer() {
IntBuffer intBuffer = IntBuffer.allocate(10); for (int i = 0; i < intBuffer.capacity(); i++) {
int randomNumber = new SecureRandom().nextInt(20);
intBuffer.put(randomNumber);
} intBuffer.flip();//翻转,从写转到读状态 while (intBuffer.hasRemaining()) {
System.out.println(intBuffer.get());
}
} /**
* @ClassName: NioTest1
* @Description: 描述 读文件
* @Author:
* @CreateDate: 2019/8/27 21:26
* @Version: 1.0
*/
@Test
public void testChannelRead() {
try {
FileInputStream fileInputStream = new FileInputStream("NioTest1.txt"); FileChannel fileChannel = fileInputStream.getChannel(); ByteBuffer byteBuffer = ByteBuffer.allocate(512); fileChannel.read(byteBuffer); byteBuffer.flip(); while(byteBuffer.remaining() > 0) { byte b = byteBuffer.get();
System.out.println("char is : " + (char) b); if((char)b == 'e') {
byteBuffer.mark();
}
} System.out.println(byteBuffer.position());
System.out.println(byteBuffer.limit());
System.out.println(byteBuffer.capacity()); byteBuffer.reset(); // System.out.println(byteBuffer.mark());
System.out.println(byteBuffer.position());
System.out.println(byteBuffer.limit());
System.out.println(byteBuffer.capacity()); fileChannel.close();
fileInputStream.close(); } catch (Exception e) {
e.printStackTrace();
}
} /**
* @ClassName: NioTest1
* @Description: 描述 写文件
* @Author:
* @CreateDate: 2019/8/27 21:25
* @Version: 1.0
*/
@Test
public void testChannelWrite() {
try{
FileInputStream fileInputStream = new FileInputStream("NioTest1.txt");
FileChannel fileChannel = fileInputStream.getChannel(); FileChannel randowFileChannel = new RandomAccessFile(new File("NioTest1.txt"),"rw").getChannel(); ByteBuffer byteBuffer = ByteBuffer.allocate(512); byte[] byteArr = "hello nio nihao!".getBytes(); byteBuffer.put(byteArr); byteBuffer.flip(); // fileChannel.write(byteBuffer); randowFileChannel.write(byteBuffer);
}catch (Exception e) {
e.printStackTrace();
}
} /**
* @ClassName: NioTest1
* @Description: 描述 读写文件
* @Author:
* @CreateDate: 2019/8/27 21:25
* @Version: 1.0
*/
@Test
public void testChannelReadAndWrite() {
try {
FileInputStream fileInputStream = new FileInputStream("input.txt");
FileOutputStream fileOutputStream = new FileOutputStream("out.txt"); FileChannel inputFileChannel = fileInputStream.getChannel();
FileChannel outputFileChannel = fileOutputStream.getChannel(); ByteBuffer byteBuffer = ByteBuffer.allocate(512); while(inputFileChannel.read(byteBuffer) != -1) { byteBuffer.flip(); outputFileChannel.write(byteBuffer); // byteBuffer.clear();
} }catch (Exception e) {
e.printStackTrace();
} } /**
* @ClassName: NioTest1
* @Description: 描述 切下部分的byteBuffer 作为一个快照,可以实现同步
* @Author:
* @CreateDate: 2019/8/27 21:24
* @Version: 1.0
*/
@Test
public void testSlice() {
try{
ByteBuffer byteBuffer = ByteBuffer.allocate(512); for (int i = 0; i < 20; i++) {
byteBuffer.put((byte)i);
}
// byteBuffer.flip(); ByteBuffer newByteBuffer = byteBuffer.slice(); byteBuffer.put((byte)'a');
byteBuffer.put((byte)'b'); // newByteBuffer.flip();
System.out.println(newByteBuffer.get(0)); // byteBuffer.put(0, (byte)9); newByteBuffer.put(0, (byte)9); System.out.println(byteBuffer.get(20)); System.out.println(newByteBuffer.get(0)); }catch (Exception e) {
e.printStackTrace();
}
} /**
* @ClassName: NioTest1
* @Description: 描述 只读的byteBuffer
* @Author:
* @CreateDate: 2019/8/27 21:24
* @Version: 1.0
*/
@Test
public void testReadonlyBuffer() { ByteBuffer byteBuffer = ByteBuffer.allocate(512);
for (int i = 0; i < 10; i++) {
byteBuffer.put((byte)i);
} ByteBuffer readOnlyBuffer = byteBuffer.asReadOnlyBuffer(); readOnlyBuffer.position(0); readOnlyBuffer.put((byte)1); } /**
* @ClassName: NioTest1
* @Description: 描述 通过直接内存,零拷贝来处理文件
* @Author:
* @CreateDate: 2019/8/27 21:23
* @Version: 1.0
*/
@Test
public void testChannelReadAndWriteDirect() {
try {
FileInputStream fileInputStream = new FileInputStream("input.txt");
FileOutputStream fileOutputStream = new FileOutputStream("out.txt"); FileChannel inputFileChannel = fileInputStream.getChannel();
FileChannel outputFileChannel = fileOutputStream.getChannel(); ByteBuffer byteBuffer = ByteBuffer.allocateDirect(512); while(inputFileChannel.read(byteBuffer) != -1) { byteBuffer.flip(); outputFileChannel.write(byteBuffer); byteBuffer.clear();
} }catch (Exception e) {
e.printStackTrace();
} } /**
* @ClassName: NioTest1 内存映射,来修改文件 而不操作buffer
* @Description: 描述
* @Author:
* @CreateDate: 2019/8/27 21:23
* @Version: 1.0
*/
@Test
public void testMapBuffer() throws Exception {
RandomAccessFile randomAccessFile = new RandomAccessFile("NioTest1.txt", "rw");
FileChannel fileChannel = randomAccessFile.getChannel(); MappedByteBuffer mappedByteBuffer = fileChannel.map(FileChannel.MapMode.READ_WRITE, 0, 5); mappedByteBuffer.put(0, (byte)'a');
mappedByteBuffer.put(3, (byte)'b'); fileChannel.close();
randomAccessFile.close();
} /**
* @ClassName: NioTest1
* @Description: 描述 测试 filelock
* @Author:
* @CreateDate: 2019/8/27 21:30
* @Version: 1.0
*/
@Test
public void testFilelock() throws Exception {
FileChannel fileChannel = new RandomAccessFile("NioTest1.txt", "rw").getChannel(); FileLock fileLock = fileChannel.lock(3, 6, false); System.out.println(fileLock.isValid());
System.out.println(fileLock.isShared());
} /**
* @ClassName: NioTest1
* @Description: 描述
* @Author:
* @CreateDate: 2019/8/27 22:36
* @Version: 1.0
*/
@Test
public void testScattering() throws Exception {
ServerSocketChannel serverSocketChannel = ServerSocketChannel.open();
SocketAddress address = new InetSocketAddress(8899);
serverSocketChannel.bind(address); SocketChannel socketChannel = serverSocketChannel.accept(); int messageLength = 2 + 3 +4;
ByteBuffer[] byteBuffers = new ByteBuffer[3]; byteBuffers[0] = ByteBuffer.allocate(2);
byteBuffers[1] = ByteBuffer.allocate(3);
byteBuffers[2] = ByteBuffer.allocate(4); while(true) {
long readLength = 0; //最大读取 messageLength 长度的字符
while(readLength < messageLength ) {
long r = socketChannel.read(byteBuffers);
readLength += r; System.out.println("byteBuffer length r is " + r);
System.out.println("readLength length r is " + readLength); Arrays.asList(byteBuffers).forEach(byteBuffer -> {
System.out.println("p:" + byteBuffer.position() + ", l: " +byteBuffer.limit());
});
} Arrays.asList(byteBuffers).forEach(byteBuffer -> {
byteBuffer.flip();
}); long writeLength = 0;
//写会去
while(writeLength < messageLength) {
long w = socketChannel.write(byteBuffers);
writeLength += w;
System.out.println("byteBuffer length w is " + w);
System.out.println("writeLength length w is " + writeLength); Arrays.asList(byteBuffers).forEach(byteBuffer -> {
System.out.println("p:" + byteBuffer.position() + ", l: " +byteBuffer.limit());
});
} Arrays.asList(byteBuffers).forEach(byteBuffer -> byteBuffer.clear()); }
} @Test
public void testSelector() throws Exception{
Selector selector = Selector.open(); int[] ports = {5000, 5001, 5002, 5003, 5004}; for (int i = 0; i < ports.length; i++) {
ServerSocketChannel serverSocketChannel = ServerSocketChannel.open();
serverSocketChannel.configureBlocking(false); //变成非阻塞的模式 很重要 // serverSocketChannel.bind(new InetSocketAddress(ports[i])); ServerSocket serverSocket = serverSocketChannel.socket();
//这个bind 直接绑在 serverSocketChannel 可以不 尝试了下,好像区别不大,都可以走通 但是不能重复绑
serverSocket.bind(new InetSocketAddress(ports[i])); serverSocketChannel.register(selector, SelectionKey.OP_ACCEPT); System.out.println("监听:" + ports[i]);
} while(true) { int number = selector.select();
System.out.println("number:" + number); Set<SelectionKey> selectionKeys = selector.selectedKeys(); Iterator<SelectionKey> keyIterable = selectionKeys.iterator(); System.out.println("selectionKeys : " + selectionKeys); while(keyIterable.hasNext()) {
SelectionKey selectionKey = keyIterable.next();
if(selectionKey.isAcceptable()) {//可接受的
ServerSocketChannel serverSocketChannel = (ServerSocketChannel) selectionKey.channel();
//这里为什么还要调accept 因为上面放进去的就是 ServerSocketChannel ,而且没有调accept 接收请求
SocketChannel socketChannel = serverSocketChannel.accept();
socketChannel.configureBlocking(false); System.out.println("获得链接:" + socketChannel); socketChannel.register(selector, SelectionKey.OP_READ);
// socketChannel.register(selector, SelectionKey.OP_READ); 重复注册好像不影响 keyIterable.remove();//如果不remove selectionKeys中会一直存在事件对象
} else if(selectionKey.isReadable()) {//可读取的
//这里就可以直接用SocketChannel来接收,因为在accept中,是用socketChannel来注册的
SocketChannel socketChannel = (SocketChannel) selectionKey.channel(); ByteBuffer byteBuffer = ByteBuffer.allocate(512);
while(socketChannel.read(byteBuffer) > 0) {
byteBuffer.flip(); System.out.println("读取到客户端的消息:" + byteBuffer);
System.out.println("读取到客户端:" + socketChannel); socketChannel.write(byteBuffer); byteBuffer.clear();
} keyIterable.remove(); } } } }
}
2、nio的例子实践的更多相关文章
- NIO模式例子
NIO模式主要优势是体现在对多连接的管理,对众多连接各种事件的转发让处理变得更加高效,所以一般是服务器端才会使用NIO模式,而对于客户端为了方便及习惯使用阻塞模式的Socket进行通信.所以NIO模式 ...
- IO模型之NIO代码及其实践详解
一.简介 NIO我们一般认为是New I/O(也是官方的叫法),因为它是相对于老的I/O类库新增的( JDK 1.4中的java.nio.*包中引入新的Java I/O库).但现在都称之为Non-bl ...
- docker-1-环境安装及例子实践
1.安装go 先新建一个Go的工作空间文件夹,文件夹路径建议放在$HOME下: userdeMacBook-Pro:~ user$ cd $HOME userdeMacBook-Pro:~ user$ ...
- python argparse例子实践
python 解析命令行读取参数,在多个文件或者不同语言协同的项目中,python脚本经常需要从命令行直接读取参数. 万能的python自带了sys.arg.argparse.optparse模块等, ...
- NIO的学习
参考 http://wenku.baidu.com/link?url=rq-BEp3Et4JRrE62f2Lv9hq8nT_Gq0XPb65h8OBqTAt-ILfqKmdjIhVEp8bctIdm0 ...
- 漫谈Java IO之 NIO那些事儿
前面一篇中已经介绍了基本IO的使用以及最简单的阻塞服务器的例子,本篇就来介绍下NIO的相关内容,前面的分享可以参考目录: 网络IO的基本知识与概念 普通IO以及BIO服务器 NIO的使用与服务器Hel ...
- MapServer Tutorial——MapServer7.2.1教程学习——第一节用例实践:Example1.2 Static Map with Two Layers
MapServer Tutorial——MapServer7.2.1教程学习——第一节用例实践:Example1.2 Static Map with Two Layers 一.前言 上一篇博客< ...
- NIO基本操作
NIO是Java 4里面提供的新的API,目的是用来解决传统IO的问题 NIO主要有三大核心部分:Channel(通道),Buffer(缓冲区), Selector(选择器) Channel(通道) ...
- JAVA NIO non-blocking模式实现高并发服务器(转)
原文链接:JAVA NIO non-blocking模式实现高并发服务器 Java自1.4以后,加入了新IO特性,NIO. 号称new IO. NIO带来了non-blocking特性. 这篇文章主要 ...
随机推荐
- MyBatis更新,删除,插入
UserMapper.java: package com.bjsxt.mapper; import java.util.List; import org.apache.ibatis.annotatio ...
- CF372C Watching Fireworks is Fun(单调队列优化DP)
A festival will be held in a town's main street. There are n sections in the main street. The sectio ...
- 每个pool pg数计算
ceph PGs per Pool Calculator 原文档:http://xiaqunfeng.cc/2017/09/18/ceph-PGs-per-Pool-Calculator/ 2017- ...
- 小白进阶—python中os模块用法
一.os模块概述 python中的os 模块包含普遍的操作系统功能,这个模块不受平台限制,即windows和linux上都适用. 二.常用方法 1.os.name 返回正在使用的平台.如果是windo ...
- 机会来了!5G时代带来新闻传播行业的变革!
5G时代到来!新闻传播行业大变革! 1.作为一名体育生进入的新闻传播学院,传统的新闻媒体能力已不再具有优势,意味着我有翻身的机会了! 从一开始进入大学,由于高中的知识储备不如其他人,尤其是英语能力方面 ...
- 修改element-ui默认属性
修改element ui默认的样式 如果要组件内全局修改 首先在浏览器里F12找到element默认的UI类名 找到要修改的默认类名以后 在文件中修改代码,重写属性 <style> .el ...
- JS基础-DOM
DOM DOM 事件的级别 DOM 事件模型 DOM 事件流 DOM 事件捕获的具体流程 Event 对象的常见应用 自定义事件 DOM概述 | MDN DOM | MDN DOM操作 DOM事件级别 ...
- Web基础了解版03-jQuery
jQuery jQuery,顾名思义,也就是JavaScript和查询(Query)极大地简化了JavaScript开发人员遍历HTML文档.操作DOM.处理事件.执行动画和开发Ajax. jQuer ...
- 更改CSDN博客皮肤的一种简易方法
CSDN改版后,皮肤设置变得不能够更改了,不过下面这种方法依然可以做到: 首先来到博客设置的主页面:. 接下来按ctrl + shift + i进入 如下页面,然后点击图中红色标记圈起来的选择元素按钮 ...
- C# WPF抽屉效果实现(C# WPF Material Design UI: Navigation Drawer & PopUp Menu)
时间如流水,只能流去不流回! 点赞再看,养成习惯,这是您给我创作的动力! 本文 Dotnet9 https://dotnet9.com 已收录,站长乐于分享dotnet相关技术,比如Winform.W ...