博客
关于我
强烈建议你试试无所不能的chatGPT,快点击我
Java IO详解(七)------随机访问文件流
阅读量:5923 次
发布时间:2019-06-19

本文共 3794 字,大约阅读时间需要 12 分钟。

File 类的介绍:

Java IO 流的分类介绍:

Java IO 字节输入输出流:

Java IO 字符输入输出流:

Java IO 包装流:

Java IO 对象流(序列化与反序列化):

 

1、什么是 随机访问文件流 RandomAccessFile?

  该类的实例支持读取和写入随机访问文件。 随机访问文件的行为类似于存储在文件系统中的大量字节。 有一种游标,或索引到隐含的数组,称为文件指针 ; 输入操作读取从文件指针开始的字节,并使文件指针超过读取的字节。 如果在读/写模式下创建随机访问文件,则输出操作也可用; 输出操作从文件指针开始写入字节,并将文件指针提前到写入的字节。 写入隐式数组的当前端的输出操作会导致扩展数组。 文件指针可以通过读取getFilePointer方法和由设置seek方法。

  通俗来讲:我们以前讲的 IO 字节流,包装流等都是按照文件内容的顺序来读取和写入的。而这个随机访问文件流我们可以再文件的任意地方写入数据,也可以读取任意地方的字节。

 

我们查看 底层源码,可以看到:

public class RandomAccessFile implements DataOutput, DataInput, Closeable {

  实现了 DataOutput类,DataInput类,那么这两个类是什么呢?

 

2、数据流:DataOutput,DataInput

  ①、DataOutput:提供将数据从任何Java基本类型转换为一系列字节,并将这些字节写入二进制流。 还有一种将String转换为modified UTF-8格式(这种格式会在写入的数据之前默认增加两个字节的长度)并编写结果字节系列的功能。

  ②、DataInput:提供从二进制流读取字节并从其中重建任何Java原语类型的数据。 还有,为了重建设施String从数据modified UTF-8格式。 

下面我们以其典型实现:DataOutputSteam、DataInputStream 来看看它的用法:

//数据输出流		File file = new File("io"+File.separator+"a.txt");		DataOutputStream dop = new DataOutputStream(new FileOutputStream(file));		//写入三种类型的数据		dop.write(65);		dop.writeChar('哥');		dop.writeUTF("帅锅");		dop.close();				//数据输入流		DataInputStream dis = new DataInputStream(new FileInputStream(file));		System.out.println(dis.read());  //65		System.out.println(dis.readChar());	//哥		System.out.println(dis.readUTF());	//帅锅		dis.close();

  

 

3、通过上面的例子,我们可以看到因为 RandomAccessFile 实现了数据输入输出流,那么 RandomAccessFile 这一个类就可以完成 输入输出的功能了。

  

这里面第二个参数:String mode 有以下几种形式:(ps:为什么这里的值是固定的而不弄成枚举形式,不然很容易写错,这是因为随机访问流出现在枚举类型之前,属于Java 历史遗留问题)

  

 

 第一种:用 随机流顺序读取数据

public class RandomAccessFileTest {	public static void main(String[] args) throws Exception {		File file = new File("io"+File.separator+"a.txt");		write(file);		read(file);	}		/**	 * 随机流读数据	 */	private static void read(File file) throws Exception {		//以 r 即只读的方法读取数据		RandomAccessFile ras = new RandomAccessFile(file, "r");		byte b = ras.readByte();		System.out.println(b); //65				int i = ras.readInt();		System.out.println(i); //97				String str = ras.readUTF(); //帅锅		System.out.println(str);		ras.close();	}	/**	 * 随机流写数据	 */	private static void write(File file) throws Exception{		//以 rw 即读写的方式写入数据		RandomAccessFile ras = new RandomAccessFile(file, "rw");		ras.writeByte(65);		ras.writeInt(97);		ras.writeUTF("帅锅");				ras.close();	}}

  

第二种:随机读取,那么我们先介绍这两个方法

这里所说的偏移量,也就是字节数。一个文件是有N个字节数组成,那么我们可以通过设置读取或者写入的偏移量,来达到随机读取或写入的目的。

我们先看看Java 各数据类型所占字节数:

下面是 随机读取数据例子:

/**	 * 随机流读数据	 */	private static void read(File file) throws Exception {		//以 r 即只读的方法读取数据		RandomAccessFile ras = new RandomAccessFile(file, "r");				byte b = ras.readByte();		System.out.println(b); //65		//我们已经读取了一个字节的数据,那么当前偏移量为 1		System.out.println(ras.getFilePointer());  //1 		//这时候我们设置 偏移量为 5,那么可以直接读取后面的字符串(前面是一个字节+一个整型数据=5个字节)		ras.seek(5);		String str = ras.readUTF(); //帅锅		System.out.println(str);				//这时我们设置 偏移量为 0,那么从头开始		ras.seek(0);		System.out.println(ras.readByte()); //65				//需要注意的是:UTF 写入的数据默认会在前面增加两个字节的长度				ras.close();	}

  

 随机流复制文件:

/**	 * 随机流复制文件	 * @param fileA	 * @param B	 * @throws Exception 	 */	private static void copyFile(File fileA,File fileB) throws Exception{				RandomAccessFile srcRA = new RandomAccessFile(fileA, "rw");		RandomAccessFile descRA = new RandomAccessFile(fileB, "rw");				//向 文件 a.txt 中写入数据		srcRA.writeByte(65);		srcRA.writeInt(97);		srcRA.writeUTF("帅锅");		//获取 a.txt 文件的字节长度		int len = (int) srcRA.length();		srcRA.seek(0);		System.out.println(srcRA.readByte()+srcRA.readInt()+srcRA.readUTF());				//开始复制		srcRA.seek(0);		//定义一个数组,用来存放 a.txt 文件的数据		byte[] buffer = new byte[len];		//将 a.txt 文件的内容读到 buffer 中		srcRA.readFully(buffer);		//再将 buffer 写入到 b.txt文件中		descRA.write(buffer);				//读取 b.txt 文件中的数据		descRA.seek(0);		System.out.println(descRA.readByte()+descRA.readInt()+descRA.readUTF());		//关闭流资源		srcRA.close();		descRA.close();	}

  

ps:一般多线程下载、断点下载都可以运用此随机流

 

转载地址:http://ozavx.baihongyu.com/

你可能感兴趣的文章
[转]npm、 cnpm、yarn
查看>>
净推荐值(NPS):用户忠诚度测量的基本原理及方法
查看>>
我终于开通了微信公众号
查看>>
Spring3:AOP
查看>>
如何将本地的项目上传到git
查看>>
java结合testng,利用mysql数据库做数据源的数据驱动实例
查看>>
C# 多线程学习系列四之ThreadPool取消、超时子线程操作以及ManualResetEvent和AutoResetEvent信号量的使用...
查看>>
银行传统支付通道与支付平台结合
查看>>
activiti5/6 系列之--Activiti与BPMN2.0规范相关节点对应关系
查看>>
【译文】抽象漏洞法则
查看>>
获取音、视频时长(NAudio,Shell32,FFmpeg)
查看>>
SNMP协议
查看>>
大二结束前的一通胡言乱语
查看>>
sf.net zurückgekommen
查看>>
Java常见疑惑和陷阱
查看>>
关于nand flash的地址 A8,寻址
查看>>
Windows Azure Cloud Service (22) Web Role的Full IIS特性
查看>>
HtmlWeb类
查看>>
LINQ之路12:LINQ Operators之数据转换(Projecting)
查看>>
OpenGL ES for Windows Mobile
查看>>