netty02-nio

1.NIO-Non Block IO (new IO) 


java1.4以后出现了NIO就是为了解决BIO线程问题

1.1基本概念


  • Non Block IO 非阻塞IO (new io)
  • Selector 通道的管理器,管理Channel
  • ServerSocketChannel(ServerSocket): 只关心客户端连接事件
  • SocketChannel(Socket):关心读事件,写事件,读写事件..
  • SelectionKey 事件集合
  • ByteBuffer

1.2 单线程Reactor模型


package com.hotpot.day01.nio;

import java.io.IOException;
import java.net.InetSocketAddress;
import java.nio.ByteBuffer;
import java.nio.channels.SelectionKey;
import java.nio.channels.Selector;
import java.nio.channels.ServerSocketChannel;
import java.nio.channels.SocketChannel;
import java.util.Iterator;

/**
 * 描述:nio
 * @author: myx
 * @date: 2018/2/6 0006
 * Copyright © 2017-ganinfo. All rights reserved.
 */
public class NioSocketDemo {
	/**
	 * 通道管理器(选择器),多个用户共用的,所以需要放到这里
	 */
	private Selector selector;
	
	/**
	 * 初始化服务端ServerSocketChannel通道,并初始化选择器
	 * 获得一个ServerSocket通道,并对该通道做一些初始化的工作
	 */
	public void initServer(int port) throws IOException {
		// 获取ServerSocket通道 , 相对于传统的ServerSocket
		ServerSocketChannel serverChannel = ServerSocketChannel.open();
		// 设置通道为非阻塞
		serverChannel.configureBlocking(false);
		// 将该通道对应的ServerSocket绑定到port端口
		serverChannel.socket().bind(new InetSocketAddress(port));
		// 获得一个通道选择器(管理器)
		this.selector = Selector.open();
		// 将通道选择器和该通道绑定,并为该通道注册SelectionKey.OP_ACCEPT事件,注册该事件后,
		// 当该事件到达时,selector.select()会返回,如果该事件没到达selector.select()会一直阻塞。
		// 意思是大门交给selector看着,给我监听是否有accpet事件
		serverChannel.register(this.selector, SelectionKey.OP_ACCEPT);
		System.out.println("服务端启动成功...");
		/*
		***SelectionKey中定义的4中事件 ***
		OP_ACCEPT —— 接收连接继续事件,表示服务器监听到了客户连接,服务器可以接收这个连接了
		OP_CONNECT —— 连接就绪事件,表示客户与服务器的连接已经建立成功
		OP_READ —— 读就绪事件,表示通道中已经有了可读的数据,可以执行读操作了(通道目前有数据,可以进行读操作了)
		OP_WRITE —— 写就绪事件,表示已经可以向通道写数据了(通道目前可以用于写操作)
		*/
		
	}

	/**
	 * 采用轮询的方式监听selector上是否有需要处理的事件,如果有,则进行处理
	 */
	public void listenSelector() throws IOException {
		// 轮询访问selector
		while (true) {
			// 当注册的事件到达时,方法返回;否则,该方法会一直阻塞
			// 多路复用  Reactor模型
			this.selector.select();
			// 无论是否有读写事件发生,selector每隔1s被唤醒一次  
			 //this.selector.select(1000);
			 //立即返回
			 //this.selector.selectNow();
			// 获得selector中选中的项的迭代器,选中的项为注册的事件
			Iterator<?> iteratorKey = this.selector.selectedKeys().iterator();
			while (iteratorKey.hasNext()) {
				SelectionKey selectionKey = (SelectionKey) iteratorKey.next();
				// 删除已选的key,以防重复处理
				iteratorKey.remove();
				// 处理请求
				handler(selectionKey);
			}
		}
	}

	/**
	 * 处理请求
	 */
	public void handler(SelectionKey selectionKey) throws IOException {
		if (selectionKey.isAcceptable()) {//处理客户端连接请求事件
			System.out.println("新的客户端连接...");
			ServerSocketChannel server = (ServerSocketChannel) selectionKey.channel();
			// 获得和客户端连接的通道
			// 完成该操作意味着完成TCP三次握手,TCP物理链路正式建立  
			SocketChannel channel = server.accept();
			// 设置成非阻塞
			channel.configureBlocking(false);
			// 在和客户端连接成功之后,为了可以接收到客户端的信息,需要给通道设置读的权限。
			channel.register(this.selector, SelectionKey.OP_READ);
		} else if (selectionKey.isReadable()) {// 处理读的事件
			// 服务器可读取消息:得到事件发生的Socket通道
			SocketChannel channel = (SocketChannel) selectionKey.channel();
			// 创建读取的缓冲区
			ByteBuffer buffer = ByteBuffer.allocate(1024);//1kb
			int readData = channel.read(buffer);
			if(readData > 0){
				String msg = new String(buffer.array(),"GBK").trim();// 先讲缓冲区数据转化成byte数组,再转化成String
				System.out.println("服务端收到信息:" + msg);
				
				//回写数据
				ByteBuffer writeBackBuffer = ByteBuffer.wrap("receive data".getBytes("GBK"));
				channel.write(writeBackBuffer);// 将消息回送给客户端
			}else{
				System.out.println("客户端关闭咯...");
				//SelectionKey对象会失效,这意味着Selector再也不会监控与它相关的事件
				selectionKey.cancel();
			}
		}
	}
	/**
	 * 启动服务端测试
	 */
	public static void main(String[] args) throws IOException {
		NioSocketDemo server = new NioSocketDemo();
		// 初始化服务端
		server.initServer(8888);
		// 服务器端监听Selector事件
		server.listenSelector();
	}
}
餐厅模型:
       一个服务员可以服务多个客户

如果一个餐厅只有一个服务员,就会出现多个客户等待问题,所以为了提高效率需要多增加服务员------->netty


1.2.1 操作系统几种事件模型


1.2.1.1 select



1.2.1.2 poll模型

同select

1.2.1.3 epoll模型


1.3 netty模型


1.3.1 Reactor


  • 单线程Reactor
  • 多线程Reactor
  • 主从多线程Reactor

1.3.2 模型图


多线程Reactor模型

主从多线程Reactor模型



  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值