• 【Java nio】Channel


      1 package com.slp.nio;
      2 
      3 import org.junit.Test;
      4 
      5 import java.io.*;
      6 import java.nio.ByteBuffer;
      7 import java.nio.CharBuffer;
      8 import java.nio.MappedByteBuffer;
      9 import java.nio.channels.FileChannel;
     10 import java.nio.charset.CharacterCodingException;
     11 import java.nio.charset.Charset;
     12 import java.nio.charset.CharsetDecoder;
     13 import java.nio.charset.CharsetEncoder;
     14 import java.nio.file.Paths;
     15 import java.nio.file.StandardOpenOption;
     16 import java.util.Map;
     17 import java.util.Set;
     18 
     19 /**
     20  * Created by sanglp on 2017/3/1.
     21  * 一、通道:用于源节点与目标节点的连接,在Java NIO中负责缓冲区中数据的传输。通道本身是不存储任何数据的,因此需要配合缓冲区进行传输数据
     22  * 二、通道的一些主要实现类
     23  * java.nio.Channel接口
     24  *     |--FileChannel
     25  *     |--SocketChannel
     26  *     |--ServerSocketChannel
     27  *     |--DatagramChannel
     28  * 三、获取通道
     29  * 1.java针对支持通道的类提供了getChannel()方法
     30  *     本地IO:
     31  *     FileInputStream/FileOutputStream/RandomAccessFile
     32  *     网络IO:
     33  *     Socket
     34  *     ServerSocket
     35  *     DategramSocket
     36  * 2.在jdk1.7中的NIO2针对各个通道提供了一个静态方法open()
     37  * 3。jdk1.7中的NIO2的Files工具类的newByteChannel()
     38  * 四、通道之间的数据传输
     39  * transferFrom()
     40  * transferTo()
     41  * 五、分散和聚集
     42  * 分散度区:将通道中的数据分散到多个缓冲区中
     43  * 聚集写入:将多个缓冲区中的数据聚集到通道中
     44  *
     45  * 六、字符集:Charset
     46  * 编码:字符串->字节数组
     47  * 解码:字节数组->字符串
     48  */
     49 public class TestChannel {
     50     @Test
     51     public void test6() throws CharacterCodingException {
     52         Charset cs1 =  Charset.forName("GBK");
     53         //获取编码器和解码器
     54         CharsetEncoder ce = cs1.newEncoder();
     55         //获取解码器
     56         CharsetDecoder cd = cs1.newDecoder();
     57 
     58         CharBuffer charBuffer = CharBuffer.allocate(1024);
     59         charBuffer.put("桑丽平加油!!");
     60         charBuffer.flip();
     61 
     62         //编码
     63         ByteBuffer byteBuffer = ce.encode(charBuffer);
     64         for (int i=0;i<12;i++){
     65             System.out.println(byteBuffer.get(i));
     66         }
     67 
     68         //解码
     69         byteBuffer.flip();
     70       CharBuffer charBuffer1 =   cd.decode(byteBuffer);
     71         System.out.println(charBuffer1.toString());
     72 
     73         System.out.println("------------------------");
     74 
     75         Charset cs2 = Charset.forName("UTF-8");
     76         byteBuffer.flip();
     77         CharBuffer  cBuf3 =cs2.decode(byteBuffer);
     78         System.out.println(cBuf3.toString());
     79     }
     80 
     81     @Test
     82     public void test5(){
     83         Map<String,Charset> map=Charset.availableCharsets();
     84         Set<Map.Entry<String,Charset>> set = map.entrySet();
     85        for (Map.Entry<String,Charset> entry :set ){
     86            System.out.println(entry.getKey()+"="+entry.getValue());
     87        }
     88     }
     89     @Test
     90     public void test4() throws IOException {
     91         RandomAccessFile randomAccessFile = new RandomAccessFile("1.txt","rw");
     92         //获取通道
     93         FileChannel channel = randomAccessFile.getChannel();
     94         //分配指定大小的缓冲区
     95         ByteBuffer buffer1 = ByteBuffer.allocate(100);
     96         ByteBuffer buffer2 = ByteBuffer.allocate(1024);
     97         //分散读取
     98         ByteBuffer [] bufs = {buffer1,buffer2};
     99         channel.read(bufs);
    100         for (ByteBuffer byteBuffer:bufs){
    101             byteBuffer.flip();
    102         }
    103 
    104         System.out.println(new String(bufs[0].array(),0,bufs[0].limit()));
    105         System.out.println("---------------");
    106         System.out.println(new String(bufs[1].array(),0,bufs[1].limit()));
    107 
    108         //聚集写入
    109         RandomAccessFile randomAccessFile1 = new RandomAccessFile("2.txt","rw");
    110         FileChannel channel1 = randomAccessFile1.getChannel();
    111         channel1.write(bufs);
    112 
    113     }
    114 
    115     //通道之间的数据传输(直接缓冲区)
    116     @Test
    117     public void test3() throws IOException {
    118         FileChannel fileChannel = FileChannel.open(Paths.get("pipe.bmp"), StandardOpenOption.READ);
    119         FileChannel outChannel =FileChannel.open(Paths.get("4.bmp"),StandardOpenOption.WRITE,StandardOpenOption.READ,StandardOpenOption.CREATE_NEW);
    120 
    121         fileChannel.transferTo(0,fileChannel.size(),outChannel);
    122         //outChannel.transferFrom(fileChannel,0,fileChannel.size());或者
    123         fileChannel.close();
    124         outChannel.close();
    125     }
    126 
    127     //2、利用直接缓冲区完成文件的复制(内存映射文件)
    128     @Test
    129     public void test2() throws IOException {
    130         FileChannel fileChannel = FileChannel.open(Paths.get("pipe.bmp"), StandardOpenOption.READ);
    131         FileChannel outChannel =FileChannel.open(Paths.get("3.bmp"),StandardOpenOption.WRITE,StandardOpenOption.READ,StandardOpenOption.CREATE_NEW);
    132         //内存映射文件
    133         MappedByteBuffer imMappedBuf = fileChannel.map(FileChannel.MapMode.READ_ONLY,0,fileChannel.size());
    134         MappedByteBuffer outMappedBuf = outChannel.map(FileChannel.MapMode.READ_WRITE,0,fileChannel.size());
    135         //直接对缓冲区进行数据的读写操作
    136         byte [] dst = new byte[imMappedBuf.limit()];
    137         imMappedBuf.get(dst);
    138         outMappedBuf.put(dst);
    139 
    140         fileChannel.close();
    141         outChannel.close();
    142 
    143     }
    144 
    145     //1、利用通道完成文件的复制(费直接缓冲区)
    146     @org.junit.Test
    147     public void test1(){
    148         FileInputStream fis =null;
    149         FileOutputStream fos =null;
    150         FileChannel inChanne=null;
    151         FileChannel outChannel=null;
    152         try{
    153        fis = new FileInputStream("pipe.bmp");
    154         fos = new FileOutputStream("2.jpg");
    155         //获取通道
    156         inChanne =fis.getChannel();
    157         outChannel = fos.getChannel();
    158         //分配指定大小的缓冲区
    159         ByteBuffer buffer = ByteBuffer.allocate(1024);
    160         //将通道中的数据存入缓冲区中
    161         while (inChanne.read(buffer)!=-1) {
    162             buffer.flip();//切换为读取数据的模式
    163             //将缓冲区中的数据写入通道
    164             outChannel.write(buffer);
    165             buffer.clear();//清空缓冲区
    166         }
    167     }catch (IOException e){
    168         e.printStackTrace();
    169     }finally {
    170         if(outChannel!=null){
    171             try {
    172                 outChannel.close();
    173             } catch (IOException e) {
    174                 e.printStackTrace();
    175             }
    176         }
    177         if(inChanne!=null){
    178             try {
    179                 inChanne.close();
    180             } catch (IOException e) {
    181                 e.printStackTrace();
    182             }
    183         }
    184 
    185         if(fis!=null){
    186             try {
    187                 fis.close();
    188             } catch (IOException e) {
    189                 e.printStackTrace();
    190             }
    191         }
    192         if(fos!=null){
    193             try {
    194                 fos.close();
    195             } catch (IOException e) {
    196                 e.printStackTrace();
    197             }
    198         }
    199     }
    200 
    201     }
    202 }
  • 相关阅读:
    文件上传Web小案例
    加密方法(MD5加密)
    解决中文乱码(不可能解决不了)
    jquery的一些常见使用方法
    Ajax的作用
    日期时间格式的转换
    前端点击复制内容
    uniapp 移动端防止点击事件穿透
    getCurrentPages 获取当前网页完整的URL
    关闭微信浏览器网页
  • 原文地址:https://www.cnblogs.com/dream-to-pku/p/6505530.html
Copyright © 2020-2023  润新知