package io.nio;
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.nio.charset.Charset;
import java.util.Iterator;
import java.util.Set;
/**
* 服务端
* @author zzh
*
*/
public class NIOSocketServer {
public static void main(String[] args) throws Exception {
//创建选择器
Selector selector = Selector.open();
//创建一个socket通道
ServerSocketChannel ssc = ServerSocketChannel.open();
//通道为非阻塞
ssc.configureBlocking(false);
//绑定端口号
ssc.bind(new InetSocketAddress("127.0.0.1", 8080));
//关注接受到客户端连接的事件
ssc.register(selector, SelectionKey.OP_ACCEPT);
//用于字节和字符的转换
Charset charset = Charset.forName("UTF-8");
//select()阻塞到至少有一个通道在你注册的事件上就绪了
while (selector.select() > 0) {
// 一次处理selector上的每个选择的SelectionKey
Set<SelectionKey> selectedKeys = selector.selectedKeys();
Iterator<SelectionKey> iterator = selectedKeys.iterator();
while (iterator.hasNext()) {
SelectionKey key = iterator.next();
//客户端连接了
if ((key.readyOps() & SelectionKey.OP_ACCEPT) == SelectionKey.OP_ACCEPT) {
ServerSocketChannel ssChannel = (ServerSocketChannel) key.channel();
SocketChannel sc = ssChannel.accept();
sc.configureBlocking(false);
sc.register(selector, SelectionKey.OP_READ);
iterator.remove();
//channal中有数据读
} else if ((key.readyOps() & SelectionKey.OP_READ) == SelectionKey.OP_READ) {
//创建缓冲区
ByteBuffer byteBuffer = ByteBuffer.allocate(1024);
SocketChannel sc = (SocketChannel) key.channel();
while (sc.read(byteBuffer) > 0) {//读数据到缓存
// byteBuffer.clear();
// int n = sc.read(byteBuffer);
// if (n <= 0) {
// break;
// }
//反转此缓冲区,调用此方法为一系列通道写入或相对获取 操作做好准备
byteBuffer.flip();
System.out.println("服务端读出了:" + charset.decode(byteBuffer));
}
iterator.remove();
}
}
}
}
}
package io.nio;
import java.net.InetSocketAddress;
import java.nio.channels.SelectionKey;
import java.nio.channels.Selector;
import java.nio.channels.SocketChannel;
import java.nio.charset.Charset;
import java.util.Scanner;
/**
* 客户端
* @author zzh
*
*/
public class NIOSocketClient {
public static void main(String[] args) throws Exception {
//Selector允许单线程处理多个 Channel
// Selector selector = Selector.open();
InetSocketAddress address = new InetSocketAddress("127.0.0.1", 8080);
SocketChannel channel = SocketChannel.open(address);
channel.configureBlocking(false);
//监测读事件
// channel.register(selector, SelectionKey.OP_READ);
Charset charset = Charset.forName("UTF-8");
Scanner scan = new Scanner(System.in);
while(scan.hasNextLine()) {
//读取键盘的输入
String line = scan.nextLine();
System.out.println("读入数据" + line);
//将内容输出到SocketChanenel中
channel.write(charset.encode(line));
}
}
}