ByteBuffer用法小结

在NIO中,数据的读写操作始终是与缓冲区相关联的.读取时信道(SocketChannel)将数据读入缓冲区,写入时首先要将发送的数据按顺序填入缓冲区.缓冲区是定长的,基本上它只是一个列表,它的所有元素都是基本数据类型.ByteBuffer是最常用的缓冲区,它提供了读写其他数据类型的方法,且信道的读写方法只接收ByteBuffer.因此ByteBuffer的用法是有必要牢固掌握的.

1.创建ByteBuffer
1.1 使用allocate()静态方法
    ByteBuffer buffer=ByteBuffer.allocate(256);
    以上方法将创建一个容量为256字节的ByteBuffer,如果发现创建的缓冲区容量太小,唯一的选择就是重新创建一个大小合适的缓冲区.

1.2 通过包装一个已有的数组来创建
    如下,通过包装的方法创建的缓冲区保留了被包装数组内保存的数据.
    ByteBuffer buffer=ByteBuffer.wrap(byteArray);

    如果要将一个字符串存入ByteBuffer,可以如下操作:
    String sendString="你好,服务器. ";
    ByteBuffer sendBuffer=ByteBuffer.wrap(sendString.getBytes("UTF-16"));

2.回绕缓冲区
  buffer.flip();
  这个方法用来将缓冲区准备为数据传出状态,执行以上方法后,输出通道会从数据的开头而不是末尾开始.回绕保持缓冲区中的数据不变,只是准备写入而不是读取.

3.清除缓冲区
  buffer.clear();
  这个方法实际上也不会改变缓冲区的数据,而只是简单的重置了缓冲区的主要索引值.不必为了每次读写都创建新的缓冲区,那样做会降低性能.相反,要重用现在的缓冲区,在再次读取之前要清除缓冲区.

4.从套接字通道(信道)读取数据
  int bytesReaded=socketChannel.read(buffer);
  执行以上方法后,通道会从socket读取的数据填充此缓冲区,它返回成功读取并存储在缓冲区的字节数.在默认情况下,这至少会读取一个字节,或者返回-1指示数据结束.

5.向套接字通道(信道)写入数据
  socketChannel.write(buffer);
  此方法以一个ByteBuffer为参数,试图将该缓冲区中剩余的字节写入信道.

 

 

-----------------------

 

ByteBuffer俗称缓冲器, 是将数据移进移出通道的唯一方式,并且我们只能创建一个独立的基本类型缓冲器,或者使用“as”方法从 ByteBuffer 中获得。ByteBuffer 中存放的是字节,如果要将它们转换成字符串则需要使用 Charset , Charset 是字符编码,它提供了把字节流转换成字符串 ( 解码 ) 和将字符串转换成字节流 ( 编码) 的方法。

private byte[] getBytes (char[] chars) {//将字符转为字节(编码)
   Charset cs = Charset.forName ("UTF-8");
   CharBuffer cb = CharBuffer.allocate (chars.length);
   cb.put (chars);
   cb.flip ();
   ByteBuffer bb = cs.encode (cb)
   return bb.array();
         }

private char[] getChars (byte[] bytes) {//将字节转为字符(解码)
      Charset cs = Charset.forName ("UTF-8");
      ByteBuffer bb = ByteBuffer.allocate (bytes.length);
      bb.put (bytes);
      bb.flip ();
       CharBuffer cb = cs.decode (bb);
  
   return cb.array();
}

通道也就是FileChannel,可以由FileInputStream,FileOutputStream,RandomAccessFile三个类来产生,例如:FileChannel fc = new FileInputStream().getChannel();与通道交互的一般方式就是使用缓冲器,可以把通道比如为煤矿(数据区),而把缓冲器比如为运煤车,想要得到煤一般都通过运煤车来获取,而不是直接和煤矿取煤。用户想得到数据需要经过几个步骤:

一、用户与ByteBuffer的交互

    向ByteBuffer中输入数据,有两种方式但都必须先为ByteBuffer指定容量

         ByteBuffer buff = ByteBuffer.allocate(BSIZE);

     a)  buff  =  ByteBuffer.wrap("askjfasjkf".getBytes())注意:wrap方法是静态函数且只能接收byte类型的数据,任何其他类型的数据想通过这种方式传递,需要进行类型的转换。

     b)  buff.put();可以根据数据类型做相应调整,如buff.putChar(chars),buff.putDouble(double)等

二、FileChannel 与 ByteBuffer的交互:

    缓冲器向通道输入数据

     FileChannel fc = new FileInputStream().getChannel();  

     fc.write(buff);

     fc.close();

三、 用户与ByteBuffer交互

    通道向缓冲器送入数据

    FileChannel fc =  new FileOutputStream().getChannel();

    fc.read( buff);

    fc.flip();

四、呈现给用户(三种方式)

  1)String encoding = System.getProperty("file.encoding");

   System.out.println("Decoded using " + encoding + ": "  + Charset.forName(encoding).decode(buff));   

  2)System.out.println(buff.asCharBuffer());//这种输出时,需要在输入时就进行编码getBytes("UTF-8")

  3) System.out.println(buff.asCharBuffer());//通过CharBuffer向ByteBuffer输入 buff.asCharBuffer().put。

 

fc.rewind();

 

转载于:https://www.cnblogs.com/android-blogs/p/5647756.html

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/457664.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

promise用法_Promise的秘密

写在前面本篇文章将会带大家从分解promise入手,一步步实现一个promise。但阅读之前需要比较熟练地了解了解用法,结合用法看文章可能更容易理解。结构先看一下简单的用法。const promise new Promise((resolve, reject) > {setTimeout(() > {resol…

SpringMVC视图解析器(转)

前言 在前一篇博客中讲了SpringMVC的Controller控制器,在这篇博客中将接着介绍一下SpringMVC视图解析器。当我们对SpringMVC控制的资源发起请求时,这些请求都会被SpringMVC的DispatcherServlet处理,接着Spring会分析看哪一个HandlerMapping定…

05_JS流程控制语句

JS流程控制语句 顺序结构 选择结构 if-else语句 var aprompt(); var bprompt(); var cprompt(); if(a && b || c){alert(); }else if(a || b || c){alert(); }else{alert(); }条件分支语句 var aprompt(); switch(a){case 1:alert("1");break;case 2:al…

ForkJoinPool 学习示例

在JAVA7之前,并行处理数据非常麻烦。第一,你得明确把包含数据的数据结构分成若干份。第二,你要将每个子部分分配给一个独立的线程。第三,你要在恰当的时候对它们进行同步避免不希望的竞争条件,等待所有线程完成&#x…

python深入_Python深入(上)

作者:Vamei 出处:http://www.cnblogs.com/vamei 欢迎转载,也请保留这段声明。谢谢!到现在为止,Python学习已经可以告一段落。下面的部分,我想讨论Python的高级语法和底层实现。这一部分的内容并不是使用Pyt…

06_JS对象

JS对象 创建对象 构造函数:var obj new Object()对象字面量:var obj {}; 不同:对象字面量可以在创建的同时为对象设置属性,最后一个属性后面不要加逗号 对象操作 添加属性:对象名.新属性名 值修改属性&#xf…

BZOJ4107 : [Wf2015]Asteroids

首先将速度相减,变成A在动而B不动,若速度为0则显然永远不会相交。 枚举A的每个点以及B的每条线段,计算这三个点共线的时刻。 将时刻排序,对于每个区间进行三分,用半平面交计算相交面积。 注意特判相交面积为0但是存在交…

Web Service 性能测试工具比较

背景 希望选择一款Web Service性能测试工具,能真实模拟大量用户访问网站时的请求,从而获取服务器当前的请求处理能力(请求数/秒)。以微信服务器为例,每个用户用独立的登录token,做各种操作,比如…

python中的常量是什么意思_第14p,Python中的常量与注释。

大家好,我是杨数Tos,这是《从零基础到大神》系列课程的第14篇文章,第二阶段的课程:Python基础知识:常量与注释。学习本课程,建议先看一遍:【计算机基础知识】课程。一、Python中的常量1、什么是…

07_JS函数

JS函数 函数声明 使用构造函数 var fun new Function();使用关键字 function 函数名(形参){// 函数体 }匿名函数 var fun1 function(){name "fun1" }函数参数 实参,形参都可以是任意数据类型,浏览器执行时不会检查实参类型和数量&…

cocoapods的安装(这真是一个神奇的东西,每次安装的方法都不一样,而且很容易出现各种各样的错误)...

文章开始之前,建议安装一个显示网速的插件,不然你不知道到底有没有下载,也让生活有一点盼头 1.因为众所周知的原因(我dang的行为真的是让人失望),先更换一下ruby镜像源 $ gem sources --remove https://rub…

转】MyEclipse使用总结——在MyEclipse中设置jsp页面为默认utf-8编码

原博文出自于:http://www.cnblogs.com/xdp-gacl/p/3496161.html        感谢! 在MyEclispe中创建Jsp页面,Jsp页面的默认编码是“ISO-8859-1”,如下图所示: 在这种编码下编写中文是没有办法保存Jsp页面的&#…

sum怎么用python_python sum()函数和.sum(axis=0)函数的使用

参考:《Machine Learning in Action》第二章#####################################################################sum函数:sum()函数是内建函数help(sum)函数功能:返回一个数字序列(非字符串)的和,并加上参数start的值(默认为…

08_JS工厂方法和构造函数

工厂方法和构造函数 工厂方法 工厂方法用来批量产生对象 function CreatCar(name,prase){// new 一个对象var obj new Object();obj.name name;obj.parse prase;obj.print function(){console.log(this.name " : " this.parse)};// 返回对象return obj; };va…

华为机试题【10】-求数字基root

题目描述: 求整数的Root:给定正整数,求每位数字之和;如果和不是一位数,则重复; 输入:输入任意一个或多个整数 输出:输出各位数字之和,直到和为个位数为止(输入异常,则返回-1),多行,每行对应一个输入数据的结果。 样例…

国内开源镜像站

搜狐开源镜像站:http://mirrors.sohu.com/ 网易开源镜像站:http://mirrors.163.com/开源中国:http://mirrors.oschina.net/首都在线科技股份有限公司:http://mirrors.yun-idc.com/阿里云开源镜像:http://mirrors.aliyu…

python update skeleton 不自动_python编程笔记(1)-数据类型

断断续续学了一些,但是后边一直没有使用,就又忘记了。为了缩短学习周期,这次学习的方法:先学主要框架(数据类型、条件、循环、函数、类、numpy、pandas、sklearn),后期直接看朋友code 实操了&am…

09_JS原型对象

原型对象 在构造函数中,同一类相同的方法可以直接写在构造函数里,但这样每实例化一个对象都会产生一个新的该方法,但其实这个方法都是一样的,这样会浪费大量空间,另外,可以将相同的方法写在构造函数外&…

[改善Java代码]非稳定排序推荐使用List

我们知道Set与List的最大区别就是Set中的元素不可以重复(这个重复指的equals方法的返回值相等),其他方面则没有太大的区别了,在Set的实现类中有一个比较常用的类需要了解一下:TreeSet,该类实现了类默认排序…

如何访问另一台电脑的共享文件夹_如何远程控制另一台电脑

在工作中,我们时常需要远程控制一下另一台电脑,如果这两台计算机在局域网内可以通过远程桌面轻松实现,如果这两台计算机不在局域网内则通常需要借助第三方软件来实现。远程桌面使用分三步:1、被控制端要开启远程桌面功能&#xff…