JavaIO操作(1)字节流和字符流1

3.2、字节流和字符流(核心)

使用File类执行的所有操作都是针对于文件本身,但是却没有针对于文件的内容,而要进行文件内容操作就需要通过Java之中提供的两组类完成:

· 字节操作流(是在JDK 1.0的时候定义的):OutputStream、InputStream;

· 字符操作流(是在JDK 1.1的时候定义的):Writer、Reader。

但是不管是字节流还是字符流的操作,本身都表示资源操作,而执行所有的资源操作都会按照如下的几个步骤进行,下面以文件操作为例(对文件进行读、写操作):

· 如果要操作的是文件,那么首先要通过File类对象找到一个要操作的文件路径(路径有可能存在,有可能不存在,如果不存在,则要创建路径);

· 通过字节流或字符流的子类为字节流或字符流的对象实例化(向上转型);

· 执行读 / 写操作;

· 最后一定要关闭操作的资源(close()),不管日后如何操作,资源永远要关闭。

3.2.1、字节输出流:OutputStream

java.io.OutputStream主要的功能是进行字节数据的输出的,而这个类的定义如下:

public abstract class OutputStream

extends Object

implements Closeable, Flushable

发现OutputStream类定义的时候实现了两个接口:Closeable、Flushable,那么这两个接口的定义如下:

CloseableJDK 1.5推出

FlushableJDK 1.5推出

public interface Closeable extends AutoCloseable {

public void close() throws IOException;

}

public interface Flushable {

public void flush() throws IOException;

}

提示:对于Closeable继承的AutoCloseable接口

AutoCloseable是在JDK 1.7的时候又增加了一个新的接口,但是这个接口的定义和Closeable定义是完全一样的,我个人认为:有可能在一些其他的类上出现了自动的关闭功能,Closeable是手工关闭,AutoCloseable属于自动关闭。

但是对于Closeable和Flushable这两个接口实话而言用户不需要关注,因为从最早的习惯对于flush()和close()两个方法都是直接在OutputStream类之中定义的,所以很少去关心这些父接口问题。

对于OutputStream类而言发现其本身定义的是一个抽象类(abstract class),按照抽象类的使用原则来讲,需要定义抽象类的子类,而现在如果要执行的是文件操作,则可以使用FileOutputStream子类完成,如果按照面向对象的开发原则,子类要为抽象类进行对象的实例化,而后调用的方法以父类中定义的方法为主,而具体的实现找实例化这个父类的子类完成,也就是说在整个的操作之中,用户最关心的只有子类的构造方法:

· 实例化FileOutputStream(新建数据):public FileOutputStream(File file) throws FileNotFoundException;

· 实例化FileOutputStream(追加数据):public FileOutputStream(File file, boolean append)

throws FileNotFoundException

当取得了OutputStream类的实例化对象之后,下面肯定要进行输出操作,在OutputStream类之中定义了三个方法:

· 输出单个字节数据:public abstract void write(int b) throws IOException;

· 输出一组字节数据:public void write(byte[] b) throws IOException;

· 输出部分字节数据:public void write(byte[] b, int off, int len) throws IOException;

范例:使用OutputStream向文件之中输出数据,输出路径:d:\hellodemo\test.txt

package cn.mldn.demo;

import java.io.File;

import java.io.FileOutputStream;

import java.io.OutputStream;

public class TestDemo {

public static void main(String[] args) throws Exception {

File file = new File("D:" + File.separator + "hellodemo"

+ File.separator + "test.txt"); // 第1步:定义文件路径

if (!file.getParentFile().exists()) { // 父路径不存在

file.getParentFile().mkdirs(); // 创建父路径

}

OutputStream output = new FileOutputStream(file); // 第2步:通过子类实例化父类

String data = "Hello World .";// 要输出的数据

output.write(data.getBytes()); // 第3步:输出数据,要将数据变为字节数组输出

output.close(); // 第4步:关闭资源

}

}

在整个的文件输出过程之中可以发现,如果现在要输出的文件不存在,那么会出现自动创建文件的情况,并且如果重复执行以上的代码,会出现新的内容覆盖掉旧内容的操作,所以下面可以使用FileOutputStream类的另外一个构造方法进行数据的追加:

package cn.mldn.demo;

import java.io.File;

import java.io.FileOutputStream;

import java.io.OutputStream;

public class TestDemo {

public static void main(String[] args) throws Exception {

File file = new File("D:" + File.separator + "hellodemo"

+ File.separator + "test.txt"); // 第1步:定义文件路径

if (!file.getParentFile().exists()) { // 父路径不存在

file.getParentFile().mkdirs(); // 创建父路径

}

OutputStream output = new FileOutputStream(file, true);// 第2步:通过子类实例化父类

String data = "Hello World .\r\n";// 要输出的数据

output.write(data.getBytes()); // 第3步:输出数据,要将数据变为字节数组输出

output.close(); // 第4步:关闭资源

}

}

如果说现在不想全部内容输出,也可以使用另外一个write()方法部分内容输出。

package cn.mldn.demo;

import java.io.File;

import java.io.FileOutputStream;

import java.io.OutputStream;

public class TestDemo {

public static void main(String[] args) throws Exception {

File file = new File("D:" + File.separator + "hellodemo"

+ File.separator + "test.txt"); // 第1步:定义文件路径

if (!file.getParentFile().exists()) { // 父路径不存在

file.getParentFile().mkdirs(); // 创建父路径

}

OutputStream output = new FileOutputStream(file); // 第2步:通过子类实例化父类

String data = "Hello World .\r\n";// 要输出的数据

output.write(data.getBytes(), 0, 5); // 第3步:输出数据,要将数据变为字节数组输出

output.close(); // 第4步:关闭资源

}

}

在OutputStream类之中所有的数据都是以字节数据为主的。

原文地址:https://www.cnblogs.com/guwenren/p/3012126.html