学习了Java的NIO框架,NIO是Java提供的非阻塞I/O,基于Channel和Buffer实现,下面给出Socket示例代码,服务端和客户端。
一、服务端代码
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;
public class NIOServer
{
/**
* 选择器
*/
private Selector selector;
/**
* 通道
*/
ServerSocketChannel serverSocketChannel;
public void initServer(int port) throws IOException
{
//打开一个通道
serverSocketChannel = ServerSocketChannel.open();
//通道设置非阻塞
serverSocketChannel.configureBlocking(false);
//绑定端口号
serverSocketChannel.socket().bind(new InetSocketAddress("localhost", port));
//注册
this.selector = Selector.open();
serverSocketChannel.register(selector, SelectionKey.OP_ACCEPT);
}
public void listen() throws IOException
{
System.out.println("server started succeed!");
while (true)
{
selector.select();
Iterator<SelectionKey> ite = selector.selectedKeys().iterator();
while (ite.hasNext())
{
SelectionKey key = ite.next();
if (key.isAcceptable())
{
SocketChannel channel = serverSocketChannel.accept();
channel.configureBlocking(false);
channel.register(selector, SelectionKey.OP_READ);
}
else if (key.isReadable())
{
recvAndReply(key);
}
ite.remove();
}
}
}
public void recvAndReply(SelectionKey key) throws IOException
{
SocketChannel channel = (SocketChannel) key.channel();
ByteBuffer buffer = ByteBuffer.allocate(256);
int i = channel.read(buffer);
if (i != -1)
{
String msg = new String(buffer.array()).trim();
System.out.println("NIO server received message = " + msg);
System.out.println("NIO server reply = " + msg);
channel.write(ByteBuffer.wrap( msg.getBytes()));
}
else
{
channel.close();
}
}
public static void main(String[] args) throws IOException
{
NIOServer server = new NIOServer();
server.initServer(8080);
server.listen();
}
}
二、客户端代码
import java.io.IOException;
import java.net.InetSocketAddress;
import java.nio.ByteBuffer;
import java.nio.channels.SocketChannel;
public class NIOClient
{
/**
* 通道
*/
SocketChannel channel;
public void initClient(String host, int port) throws IOException
{
//构造socket连接
InetSocketAddress servAddr = new InetSocketAddress(host, port);
//打开连接
this.channel = SocketChannel.open(servAddr);
}
public void sendAndRecv(String words) throws IOException
{
byte[] msg = new String(words).getBytes();
ByteBuffer buffer = ByteBuffer.wrap(msg);
System.out.println("Client sending: " + words);
channel.write(buffer);
buffer.clear();
channel.read(buffer);
System.out.println("Client received: " + new String(buffer.array()).trim());
channel.close();
}
public static void main(String[] args) throws IOException
{
NIOClient client = new NIOClient();
client.initClient("localhost", 8080);
client.sendAndRecv("I am a client");
}
}
三、测试
首先启动服务端,再启动客户端,输出如下:
服务端输出
server started succeed!
NIO server received message = I am a client
NIO server reply = I am a client
客户端输出
Client sending: I am a client
Client received: I am a client
参考文档