file文件操作2-字节流和字符流

字节流和字符流

  • Java流
    • 字符流操作
      • 使用字符流读取文件
      • 使用字符流写文本文件
    • 字节流操作
      • 使用字节流读取文本文件
      • 使用字节流写文本文件

Java流

我们知道了如何利用file类对文件或者目录属性进行操作,但File类不能访问文件的内容,即不能从文件中读取数据或向文件里写数据。
读文件,是指把文件的数据读取到内存中,反之写文件就是把内存中的数据写到文件中。
流呢,是指一连串流动的字符,是以先进先出的方式发送和接收数据的通道。
在java.io包中,封装了许多输入\输出流API。在程序中,这些输入输出流的类的对象成为流对象。可以通过这些流对象将内存中的数以流的方式写入文件,也可以通过流对象将文件中的数据以流的方式读取到内存。
流对象构造的时候往往会和数据源联系起来。数据源分为源数据流和目标数据流源。
1.输入流联系的是源流数据源
2.输出流联系的则是目标数据源。
按照不同的分类方式,可以将流分成不同的类型。
1.按照流的流向进行划分可以分成输入流和输出流。
输出流:OUTPutStream和Writter作为基类。只能向其中写入数据,不能读。
输入流:InputStream和Reader作为基类。只能读取数据,不能写。
2.按照所操作的数据单元的不同,流又可以分成字节流和字符流。
字节流操作的最小的数据单位为8位字节,而字符流操作的最下数据单元是16位字符。
字节流和字符流的区分也很简单,字节流建议使用于二进制数据操作,而字符流用于文本。他们的用法几乎一样。

字符流操作

使用字符流读取文件

1.字符流输入流Reader类
Reader类是读取字符流的抽象类,他提供了常用的方法。
int read() 输入流中读取单个字符
int read(byte[] c)从输入流中读取c.length长度的字符,保存到字符数组C中,返回实际读取的字符数。
read(char[] c,int off,int len)从输入流中读取最多len的长度字符,保存到字符数组c中,保存的位置从off位置开始,返回实际读取的字符长度。
close() 关闭流
2.字符输入流FileReader类
FileReader类是Reader的子类,常用的构造方法格式如下。
FileReader(String fileName)其中,fileName是指要从中读取数据文件的名称。使用的方法如下:

Reader fr=new FileReader(“C:\\myTest.txt”);

3.使用FileReader读取文件
使用字符流类FileReader读取文本文件的操作如下。
1.引入类

import java.io.File;
import java.io.FileNotFoundException;
import java.io.FileReader;
import java.io.IOException;
import java.io.Reader;

2.创建FileReader对象

Reader re = new FileReader("C:\\mytest.txt");

3.利用FileReader类方法读取文本文件
int read();//读取单个字符
4.关闭相关的流对象
fr.close();

l练习:

Reader fe=null;
		StringBuffer sbf=null;
		try {
			fe=new FileReader("hello.txt");
			char ch[]=new char[1024];//创建字符数组作为中转站
			sbf=new StringBuffer();
					int lenth=fe.read(ch);//将字符读入数组
					while((lenth!=-1)){
						sbf.append(ch);//追加字符
						lenth=fe.read();
					}		
		} catch (Exception e) {
			// TODO Auto-generated catch block
			e.printStackTrace();
		}finally{
			if(fe!=null){
				try {
					fe.close();
				} catch (IOException e) {
					// TODO Auto-generated catch block
					e.printStackTrace();
				}
			}
		}

创建字符的中转站,存入每次读取的数据内容,然后调用FileReader对象的Read()方法将字符读入数组ch,并追加到字符串sbf中。

或者我们可以这样写:

char[] cbuf = new char[5];
		int len = 0;
		try {
			fileReader = new FileReader(file);
		} catch (FileNotFoundException e) {
			e.printStackTrace();
		}
		try {
			while ((len = (fileReader.read(cbuf))) != -1) {
				String str = new String(cbuf, 0, len);
				System.out.println(str);
			}

上面我们演示了FileReader类读取文件。而开发中,我们会将FileReader类和BufferReader类结合使用。提高文件的效率。

4.字符输入流BufferedReader类
BufferedReader类是Reader的子类,它与FileReader类的区别在于BufferReader类带有缓冲区,它可以先把一批数据读到缓冲区,接下来的读操作都是从缓冲区内获取数据,避免每次都从数据源读取数据进行字符编码转换,从而提高读取操作的效率。BufferedReader类常用的构造方法如下。
BufferedReader(Reader in);
使用此方法创建字符输入对象如下。

Reader fr=new FileReader(“C:\\mytest.txt”);
BufferedReader br=new BufferedReader(fr);

其中br就是创建的一个使用默认大小输入缓冲区的缓冲字符输入流。
5.使用FileReader和BufferedReader读取文本文件。
具体操作如下;
1.引入相关类
2.创建一个BufferedReader对象
3.利用BufferedReader类的方法读取文本文件的数据。
4.关闭相关的流对象。
测试代码:

public static void main(String[] args) {
		// TODO Auto-generated method stub
		Reader fe=null;
		BufferedReader br=null;
		try {
			fe=new FileReader("hello.txt");
			br=new BufferedReader(fe);
					String lenth=br.readLine();//读取行内容
					while(lenth!=null){
						System.out.println(lenth);
						lenth=br.readLine();
					}
		} catch (Exception e) {
			System.out.println("文件不存在");
		}finally{
				try {
					if(br!=null){
						br.close();
					}
					if(fe!=null){
					fe.close();
					}
				} catch (IOException e) {
					e.printStackTrace();
				}	
		}
	}

使用字符流写文本文件

1.字符流输出Writer
writer类是向文件写入数据流的字符流,它提供了常用的方法。
writer(string str)将str字符串里包含的字符输出到指定的输出流中
writer(String str,int off,int len)将str字符串里从off位置开始长度为len的字符输出到输出流中。
close()关闭输出流
flush()刷新输出流
2.字符输出流FileWriter类
FileWriter类是Reader的子类,常用的构造方法如下:
FileWriter(String fileName)
其中,filename表示与系统有关的文件名,使用此构造方法创建字符流输出流对象如下。
Writer fr=new FileWriter(“C:\myTest.txt”);
3.使用FileWriter写文本文件
使用FileWriter将数据写入文本文件的步骤如下。
1.引入相关类
2.创建一个FileWriter对象
3.利用FileWriter类的方法写文本文件。
4.相关流对象的清空和关闭。
4.字符输出流BufferedWriter类
同理BufferedWriter也是Writer的子类。其他的情况和上面的BufferedReader类相同。
5.BufferedWriter和FileWriter写文本文件
步骤其实是和上面相同。直接练习显示

try{fw=new FileWriter("hello.txt");
			bw=new BufferedWriter(fw);
					bw.write("大家好");
					bw.write("dsafdfa");
					bw.newLine();//插入换行
					bw.write("dthadsn");
					bw.write(123);
					bw.flush();//刷新流
					bw.close();//关闭流
	}				

字节流操作

使用字节流读取文本文件

1.字节输入流InputStream类
字节输入流InputStream的作用就是将文件中的数据输入到内部存储器(内存)中,它提供了一系列和读取数据有关的方法,常用的方法如下。
int read() 读取一个字符
int read(byte[] b)将数据读到字节中
int read(byte[] b,int off,int len)从输入流中读取最多len长度的字节,保存到字节数组b中,保存的位置从off开始。
void close() 关闭输入流
int availabe() 返回输入流读取的估计字节数
无参的read()方法从输入流读取一个八位的字节,把它转换为0~255的整数返回。
有参的两个read()方法从输入流批量读取若干字节。从文件或键盘读数据时,采用read(byte[] b)或者int read(byte[] b,int off,int len)方法可以减少进行物理读文件或键盘的次数,提高输入输出操作效率。
2.字节输入流FileInputStream类
在实际应用中,我们通常使用InputStream的子类FileStream类来实现本文文件内容的读取,常用的构造方法如下。
1)FileinputStream(File file)。其中,file指定文件数据源。使用此构造方法创建文件输入流对象如下。

File file=new File(“C:\\myTest.txt”);
InputStream fileObject=new FileInputStream(file);

此时的文件输入流对象fileObject就和数据源(“C:\myTest.txt”);联系起来了。
2)FileInputStream(String name)。其中,name指定文件数据源包含路径信息。使用此构造方法创建文件输入流对象如下。

InputStream in =new FileInputStream(“C:\\myTest.txt”);

3.使用FileInputStream读取文件
使用FileInputStream读取文件具体操作如下。
1)引入相关类

import java.io.File;
import java.io.FileInputStream;
import java.io.IOException;
import java.io.InputStream;

2)创建一个文件输入流对象

InputStream fileObject=new FileInputStream(“C:\\myTest.txt”);

3)利用文件输入的方法读取文本文件的数据。

fileObject.avaliable()//可读取的字节数
fileObject.read()//读取文件的数据

4)关闭文件输入流对象。

fileObject.close();

下面我们示例学习一下。首先,我们创建一个文件,hello.txt,然后文件保存的内容为abc,然后输出到控制台上。
示例:

FileInputStream fis=null;
		try{
			fis=new FileInputStream("hello.txt");
			int data;
			System.out.println("可读取的字节数"+fis.available());
			System.out.println("文件内容为:");
			while((data=fis.read())!=-1){
				System.out.println(data+" ");
			}
		}catch (Exception e) {
			// TODO: handle exception
			e.printStackTrace();
		}finally{
			if(fis!=null){
				try {
					fis.close();
				} catch (IOException e) {
					e.printStackTrace();
				}
			}
		}

发现输出的东西和文件中的东西不一致,那是因为InputStream和read方法是从输入流读取一个八位字节,把它转换为0~255的整数返回。abc各占一个字节所以输出的整数就是97 98 99.

注意:使用FileInputStream类读文件数据的时候还要注意下面方面。
1)read()方法返回整数,若读取的是字符串,则需要强制类型转换。例如如果想正常输出abc则要修改语句System.out.print((char)data+" ");
2)流对象使用完毕之后要关闭。

使用字节流写文本文件

1.字节输出流OutputStream类
字节输出流OutputStream类的作用是把内存中的数据输出到文件中,它提供了一系列文件中写数据的有关方法。常见的方法如下。
void write(int c)写入一个字节数据
void write(byte[] buf)写入数组buf的所有字节
void write(byte[] b,int off,int len)将字节数组从off位置开始,长度为len的字节数据输出到输出流中。
void close() 关闭输出流
2.字节输出流FileOutputStream类
我们通常使用OutputStream的子类FileOutputStream类来实现向文本文件写入数据,常用的构造方法有以下三个。
1)FileOutputStream(File file)。其中,file指定文件目标数据源。使用此构造方法创建文件输出流对象如下。

File file=new File(“C:\\myTest.txt”);
FileOutputStream fos=new FileOutputStream(file);

此时的文件输出流fos就和目标数据源(“C:\myTest.txt”)联系起来。
2)FileOutputStream(String name)。其中,name指定目标文件数据源,包含路径信息。

FileOutputStream fos=new FileOutputStream(“C:\\myTest.txt”);

3)FileOutputStream(String name,boolean append)。其中,name指定目标文件数据源,包含路径信息。append表示是否在文件末尾添加数据,若设置为true,则在文件末尾添加数据。使用此构造方法创建文件输出流对象如下。

FileOutputStream fos=new FileOutputStream(“C:\\myTest.txt”,true;

要注意的是第一种方法和第二种构造方法在向文件写数据时将覆盖文件中原有内容。另外,在使用FileOutputStream的构造方法创建FileOutputStream实例时,如果相应的文件并不存在,就会自动创建一个空的文件。若参数file或name表示的文件路劲尽管存在,但是代表一个文件目录,则此时会抛出FileNotFoundException异常。

3.使用FileOutputStream写文本文件
使用FileOutputStream向文本文件中写入数据的具体使用步骤。
1)引入相关的类。

import java.io.FileOutputStream;
import java.io.IOException;
import java.io.OutputStream;

2)构造一个文件输出流对象

OutputStream fos=new FileOutputStream(“C:\\myTest.txt”);

3)利用文件输出流的方法把数据写入文本文件中

String str=“好好学习”;
byte[] words =str.getBytes[];
fos.write(words,0,words.length);

4)关闭文件输出流

fos.close();

下面示例是具体的应用。

	FileOutputStream fos=null;
		try {
			String str="学习xuexi";
			byte[] words=str.getBytes();//字节数组
			fos=new FileOutputStream("hello.txt");//写文件
			fos.write(words,0,words.length);
			System.out.println("hello 文件已经更新了");
		} catch (Exception e) {
			e.printStackTrace();
		}finally{
			if(fos!=null){
				try {
					fos.close();
				} catch (IOException e) {
					e.printStackTrace();
				}
			}
		}
	}

首先将要写入文件的字符串通过getBytes()方法转换成字节数组words,然后调用输出流对象的write()方法,将字节数组words中的内容添加到文件(“hello.txt”)的末尾。

注意:

// 字节流处理 ( .jpg .mp3 .mp4 .avi .doc .ppt)
// 字符流 处理 (.txt .java)字符流

同理,字符流中也有缓冲输入输出 BufferedInputStream 和 BufferedOutputStream
使用方式和字节流也一样。
示例复制音乐:

public  void  BufferedTest() {
		File file1 = new File("admin.mp3");
		File file2=new File("tom.mp3");
		FileInputStream fileInputStream=null;
		FileOutputStream fileOutputStream=null;
		try {
			fileInputStream = new FileInputStream(file1);
		} catch (FileNotFoundException e) {
			e.printStackTrace();
		}
		try {
			fileOutputStream = new  FileOutputStream(file2);
		} catch (FileNotFoundException e) {
			e.printStackTrace();
		}
		BufferedInputStream bufferedInputStream = new BufferedInputStream(fileInputStream);
		BufferedOutputStream bufferedOutputStream = new  BufferedOutputStream(fileOutputStream);
		byte  [] buffer=new byte[1024];
		int len=0;
		try {
			while((len=bufferedInputStream.read(buffer))!=-1) {	
				bufferedOutputStream.write(buffer, 0, len);
				
			}
		} catch (IOException e) {
			e.printStackTrace();
		}
		if(fileInputStream!=null) {
			try {
				fileInputStream.close();
			} catch (IOException e) {
				e.printStackTrace();
			}
		}
		if(fileOutputStream!=null) {
			try {
				fileOutputStream.close();
			} catch (IOException e) {
				e.printStackTrace();
			}
		}
	}

你可能感兴趣的:(file文件操作2-字节流和字符流)