当前位置: 代码迷 >> 综合 >> 使用NIO在网络上传输文件
  详细解决方案

使用NIO在网络上传输文件

热度:10   发布时间:2023-10-15 07:27:41.0

NIO,官方说法为New IO,我们也可以理解为Non Blocking IONIO需要JDK1.7以上支持。

package channel;import java.io.File;
import java.io.FileInputStream;
import java.io.FileOutputStream;
import java.io.IOException;
import java.net.InetSocketAddress;
import java.nio.ByteBuffer;
import java.nio.channels.FileChannel;
import java.nio.channels.SelectionKey;
import java.nio.channels.Selector;
import java.nio.channels.ServerSocketChannel;
import java.nio.channels.SocketChannel;
import java.util.Date;
import java.util.Iterator;
import java.util.Set;
import org.junit.Test;public class TestNIO {@Testpublic void client(){try {SocketChannel sc = SocketChannel.open(new InetSocketAddress("127.0.0.1", 8080));//设置为非阻塞模式sc.configureBlocking(false);FileInputStream fis = new FileInputStream(new File("1.jpg"));FileChannel inChannel = fis.getChannel();			ByteBuffer dst = ByteBuffer.allocate(1024);while(inChannel.read(dst) != -1){dst.flip();sc.write(dst);dst.clear();}inChannel.close();fis.close();sc.close();} catch (IOException e) {e.printStackTrace();}		}@Testpublic void test2(){try {SocketChannel sc  = SocketChannel.open(new InetSocketAddress("127.0.0.1", 8080));sc.configureBlocking(false);ByteBuffer src = ByteBuffer.allocate(1024);src.put(new Date().toString().getBytes());src.flip();sc.write(src);src.clear();sc.close();} catch (IOException e) {e.printStackTrace();}}@Testpublic void server(){try {ServerSocketChannel ssc = ServerSocketChannel.open();//1//设置为非阻塞模式ssc.configureBlocking(false);//2ssc.bind(new InetSocketAddress(8080));//3ByteBuffer buf = ByteBuffer.allocate(1024);			FileOutputStream fos = new FileOutputStream(new File("2.jpg"));FileChannel outChannel = fos.getChannel();SocketChannel sc = null;//用open()获取选择器Selector selector = Selector.open();//4/**注册通道到选择器上,指定监控状态(SelectionKey选择键)* SelectionKey.OP_ACCEPT---接收事件* SelectionKey.OP_CONNECT---连接事件* SelectionKey.OP_READ---读事件* SelectionKey.OP_WRITE---写事件* 若监听事件不止一个时,可以使用"位或"操作符连接;int ops = SelectionKey.OP_ACCEPT | SelectionKey.OP_READ;*/			ssc.register(selector, SelectionKey.OP_ACCEPT);//5//轮询获取选择器上准备就序的监听事件while(selector.select() > 0){//selector.select()>0说明至少有一个通道准备就序Set<SelectionKey> keys = selector.selectedKeys();Iterator<SelectionKey> its = keys.iterator();while(its.hasNext()){SelectionKey selectionKey = its.next();//遍历所有准备就序的监听事件SelectionKey,并进行判断if(selectionKey.isAcceptable()){//可以启动单独的线程来处理//若接收就序就打开服务端连接sc = ssc.accept();sc.configureBlocking(false);sc.register(selector, SelectionKey.OP_READ);						//...后序读操作}else if(selectionKey.isConnectable()){//可以启动单独的线程来处理}else if(selectionKey.isReadable()){//可以启动单独的线程来处理sc = (SocketChannel) selectionKey.channel();//sc.configureBlocking(false);//sc.register(selector, SelectionKey.OP_READ);int len = -1;while((len = sc.read(buf))!= -1){buf.flip();outChannel.write(buf);buf.clear();				}}else if(selectionKey.isWritable()){//可以启动单独的线程来处理}}//selectionKey用完后取消掉its.remove();}outChannel.close();fos.close();sc.close();ssc.close();} catch (IOException e) {e.printStackTrace();}}
}


  相关解决方案