RandomAccessFile随机IO在java中是一个重要的IO类,与传统的IO类相比有很多特点:

1.集成了IO读写方法,运用这个类就可以对文件内容进行读写操作。

2.   getFilePointer()方法,可以获取当前文件读取/写入的位子,类似于获取文件中当前光标位置。

3.   seek(pos),指定文件的光标位置,通俗点说就是指定你的光标位置然后下次读文件数据的时候从该位置读取。

有了这个特性,可以实现一些操作,例如文件断点续传:文件下载过程中网断了,记录文件下载位置下次网连接上了直接从该位置开始下载;

多线程下载文件:或将一个大的文件分成多个部分,然后用多线程每个线程负责读取/写入其中一段。

4.  FileChannel 它返回的就是nio通信中的file的唯一channel

RandomAccessFile raf= new RandomAccessFile("filePath","rw");FileChannel fileChannel = raf.getChannel();

java  NIO核心组成是:

1).  channel:管道,与stream相比它是双向的,是面向缓冲区ByteBuffer的,对应于stream的输入流,是ByteBuffer从channel读入数据,对应于stream的输出流,是ByteBuffer从channel写出数据 。

inputstream  ---->fileChannel.read(buf)

outputstream  ----->fileChannel.write(buf)

2).   ByteBuffer缓存区,大致分为三类:

ByteBuffer/DirectByteBuffer/MappedByteBufferByteBuffer:ByteBuffer.allocate(1024);            是存储在JVM堆空间的缓存区,优点是java用户态创建,            创建速度快,有jvm垃圾回收机制控制缓存区的回收。            缺点是占用jvm堆空间内存,增加jvm垃圾回收负担,            在文件上传或下载时需要调用操作系统read()/write()            函数,将缓存区数据copy到用户态内存空间(如read())/            内核态内存空间(如write()函数),IO操作效率不高,            尤其是大文件。 DirectByteBuffer:ByteBuffer.allocateDirect(1024);            是在堆外申请了内存,缓存区存储在内核态内存中而不在            堆空间,通过虚拟内存地址,直接操作内核态内存空间            缓存区数据,IO操作不需要调用read()/write()系统            函数(0copy操作),并且不占用堆空间内存。            java是通过调用unsafe类实现的。MappedByteBuffer:虚拟内存映射,通过虚拟内存地址操作系统内存空间                  缓存区数据,利用操作系统的内存的缺页中断机制                  来加载文件系统的数据到内存中,MappedByteBuffer                  是个抽象类,其实现类是DirectByteBuffer。实际                  操作的类也是DirectByteBuffer类。

在进行文件上传下载时应用 DirectByteBuffer/MappedByteBuffer,不仅

逼格很高,而且速度也会得到提高,尤其是对于大型文件。

3)   Selector待续。。。

FileChannel代码示例:

1)DirectByteBuffer上传文件

RandomAccessFile raf = null;try {raf = new RandomAccessFile("test.txt", "rw");            //获取fileChannelFileChannel fileChannel = raf.getChannel();// 申请直接内存,大小1024字节ByteBuffer buf = ByteBuffer.allocateDirect(1024);// ByteBuffer读入数据int bytesRead = fileChannel.read(buf);while (bytesRead != -1) {// ByteBuffer由读状态转为写状态   buf.flip();while (buf.hasRemaining()) {// buf获取数据                System.out.print((char) buf.get());}            //     //压缩此缓冲区,将buffer中未读取的数据移到buffer前面 //                //将光标指向最后一个没有读取的下一个位置      buf.compact();// buf读数据,向buf写数据          bytesRead = fileChannel.read(buf);}} catch (IOException e) {e.printStackTrace();} finally {try {if (aFile != null) {aFile.close();}} catch (IOException e) {e.printStackTrace();} }

2)MappedByteBuffer 下载文件

   RandomAccessFile raf = new RandomAccessFile("test.txt", "rw");FileChannel fileChannel = raf.getChannel();String msg = "你好,world!";// 内存映射区域总大小        long size = msg.getBytes().length * COUNT;//READ_WRITE可以读写的ByteBufferMappedByteBuffer map = fileChannel.map(FileChannel.MapMode.READ_WRITE, 0, size);for (int i = 0; i < COUNT; i++) {map.put(msg.getBytes());raf.close();}

3)补充:

a)使用DirectByteBuffer/MappedByteBuffer,文件是存储在操作系统缓存页cachePage,写入磁盘是由操作系统控制的,如果cachePage还没有刷新到磁盘,如果系统正常关机,那么cachePage会刷到磁盘后再关机没有问题,但是如果是操作系统断电了,那就悲剧了!因为一些cachePage没写入磁盘,会导致一些文件丢失。

解决:1.通过命令将pageCache刷新到磁盘,但是会影响系统性能

2.啥都不用管,依赖操作系统,效率佳,可能是断电这事比较少见吧。

b)虚拟内存是啥?

虚拟内存是操作系统的内存管理机制,linux操作系统为每个系统进程如java进程,分配一个虚拟内存,虚拟内存是逻辑内存,理论大小是2^32(32位操作系统),2^64(64位操作系统)。虚拟内存与实际物理内存是通过虚拟内存地址(逻辑地址)+MMU(内存管理硬件)得出实际物理内存地址。

将文件转为stream流_NIO之文件IO相关推荐

  1. 如何把MapGIS的区文件转为ArcGIS的SHAPE面文件

    如何把MapGIS的区文件转为ArcGIS的SHAPE面文件 可能的应用场景:未有第三方转换软件的情况下,需要把WP文件转为SHAPE文件,在转换的过程,还要确保中不能丢失属性.不能有拓扑错误. 操作 ...

  2. Stream流、FiLe和IO流、IO流(字节流-拷贝文件_和_字符流-读取文本中的数据写入文本文件中)9-10-11

    package com.streamdemo; import java.util.ArrayList; import java.util.List; /*** 体验Stream流** 创建一个集合,存 ...

  3. mysql+视频文件转成流_视频文件自动转rtsp流

    最近碰到一个项目需要用到 rtsp 视频流做测试, 由于真实环境的 摄像头 并不能满足需求,故尝试了一下用本地视频文件转换成rtsp视频流做测试,记录一下~ 采用方案: Docker + EasyDa ...

  4. Java8新特性——Stream流:不同于IO流的流,操作集合数据

    文章目录 Stream流 1.认识Stream流(源码说明) 1.1.Stream流和Collection的区别 1.2.流的获取方式 1.3.流操作和管道 1.4.并行性 1.5.不干扰内政 1.6 ...

  5. html文件转为txt,html转txt文件怎么实现?html转txt的方法详解!

    HTML转TXT很简单,需要一台计算机即可操作,只需要把网页HTML文档的扩展名.html改成TXT文本格式的扩展名,即可用记事本打开. 如果没有显示扩展名的需要计算机设置显示扩展名. 下面我们介绍如 ...

  6. java解析时已到达文件结尾_IO流读取到文件末尾继续读取

    import java.io.BufferedInputStream; import java.io.BufferedOutputStream; import java.io.File; import ...

  7. 怎么利用迭代器写入mysql_流迭代器实现文件操作(读取和写入)方法详解

    流迭代器并不知道底层流的特性.当然,它们只适用于文本模式,否则它们不会关心数据是什么.流迭代器可以以文本模式来读写任何类型的流.这意味着除了其他的一些流之外,我们可以用迭代器以文本模式来读和写文件.在 ...

  8. 利用Python将WEBVTT格式的视频字幕文件转为SRT格式

    1 WebVTT & SRT 格式 WebVTT字幕格式与SRT字幕格式主要区别在于时间格式的区分. 下面是一个WebVTT格式的字幕文件 WEBVTT1 00:00:20.000 --> ...

  9. Yolo v5的txt标注文件转为coco格式的json标注文件

    社区上将coco数据集格式的json标注文件转为yolo的txt格式的文章较多,但是如何将txt转为json博主并没有发现.这篇文章就给大家提供一个很方便的小脚本,实现这个功能. 需要注意的是,如果直 ...

最新文章

  1. 黑客必知的SQL语句 黑客知道,程序员必知
  2. HDU 2457 DNA repair (AC自动机+DP)
  3. 从centos7默认安装的/home中转移至根目录/ (LVM操作简明教程)
  4. 阿里巴巴2018年纳税516亿元,稳居行业第一名,大家怎么看?
  5. Zookeeper超详细的面试题
  6. Hellohao全网对象存储图床源码
  7. Qt Creator 设置默认编码格式为 UTF-8
  8. [转载] Python从字符串中删除字符
  9. Atitit 项目范围管理 目录 1. 应该包含下面过程:启动、范围计划、范围定义、范围核实及范围变更控制 1 1.1. 项目范围管理的五个过程 1 2. 启动过程 1 2.1. 项目章程(如质量、
  10. lopatkin俄大神精简中文系统Windows 10 1607 Enterprise LTSB 2016 x86-x64 ZH-CN 2x1
  11. 直播常见协议概念说明
  12. 廊坊市博实计算机网络工程有限公司,IP网络终端功放T-7760(含数字IP网络平台终端嵌入软件)...
  13. Language Models are Unsupervised Multitask Learners翻译
  14. 机器学习岗位面试总结:简历应该关注的5个重点
  15. 前端HTML转PDF生成的PDF上边会有留白,下边截取不全
  16. MATLAB 相机标定中标定板角点像素坐标系到世界坐标系的转换
  17. java计算机毕业设计基于springboo个人家庭理财记账管理系统
  18. 人工智能调研报告汇总
  19. Speckle+IFC.js:开源BIM
  20. 中医蒸来大健康,科技妙在有古方

热门文章

  1. BZOJ3209(n的二进制表示中1的个数的乘积)
  2. mannachar(马拉车)求最长回文子串
  3. 使用 Minidumps 和 Visual Studio .NET 进行崩溃后调试
  4. 如何多次读取request请求里的数据
  5. 网络协议,我明明学过的呀?
  6. 音视频技术开发周刊 | 198
  7. QoE驱动的端到端视频直播技术演进
  8. Linux的内存理解
  9. 《Go语言圣经》学习笔记 第六章 方法
  10. 聚焦新基建,腾讯云十余项自研技术应用集中亮相