本节目标:
1.掌握流的概念
2.掌握字节流与字符流的作用
3.掌握文件的标准操作步骤
4.掌握字节与字符的操作的区别
1. 流
在程序中,所有的数据都是以流的方式进行传输和保存的,程序需要数据的时候需要输入流读取数据,而当程序需要将数据保存起来的时候,需要输出流完成。如下图所示。
2. 字节流与字符流
在java.io 包中,操作文件内容的主要有两大类:字节流、字符流。两类都分为输入和输出操作。字节流输出数据主要是使用OutputStream完成,输入使用InputStream完成;字符流输出数据主要是使用Writer类完成,输出数据使用Reader类完成。
以文件操作为例,操作流程为:
1)使用File类打开一个文件
2)通过字节流或字符流的子类,指定输出的位置
3)进行读/写操作
4)关闭输入/输出流
注意:使用File类时注意分隔符问题;以上四个类都是抽象类;IO操作属于资源操作,对于资源操作,操作完后必须关闭,否则可能会出现未知的错误。
3.字节流
常用的字节流总结,参考博文,点击这里
字节流主要是操作byte类型数据,以byte数组为准,主要操作类时字节输入流InputStream、字节输出流OutputStream.
3.1 字节输出流-OutputStream
OutputStream是整个io包中字节输出流的最大父类,此类定义如下:
public abstract class OutputStream extends Object implements Closeable, Flushable
可以发现,此类是一个抽象类,如果要使用此类,需要通过子类实例化对象,如果操作的是一个文件,可以使用FileOutputStream类实例化。
FileOutputStream(File file
)
创建一个向指定 File 对象表示的文件中写入数据的文件输出流,覆盖原先文件内容。
FileOutputStream(File file, boolean append
)
创建一个向指定 File 对象表示的文件中写入数据的文件输出流,追加内容。
public class OutputStreamDemo1 {
public static void main(String[] args) throws IOException {
//1.使用File类找到一个文件
File f = new File("f:" + File.separator + "test.txt");
//2.实例化输出流对象
OutputStream out = new FileOutputStream(f);
//3.写操作
String str = "Hello World!";
byte[] b = str.getBytes();
out.write(b);
//4.关闭流
out.close();
public class OutputStreamDemo2 {
public static void main(String[] args) throws IOException {
//1.使用File类找到一个文件
File f = new File("f:" + File.separator + "test.txt");
//2.实例化输出流对象
OutputStream out = new FileOutputStream(f);
//3.写操作
String str = "Hello World!!";
byte[] b = str.getBytes();
for (int i = 0; i < b.length; i++) {//采用循环方式写入
out.write(b[i]);//每次只写一个字节
}
//4.关闭流
out.close();
}
}
在文件中在追加数据,且换行追加:
public class OutputStreamDemo2 {
public static void main(String[] args) throws IOException {
//1.使用File类找到一个文件
File f = new File("f:" + File.separator + "test.txt");
//2.实例化输出流对象
OutputStream out = new FileOutputStream(f,true);
//3.写操作
String str = "\r\nHello World!!";
byte[] b = str.getBytes();
for (int i = 0; i < b.length; i++) {//采用循环方式写入
out.write(b[i]);//每次只写一个字节
}
//4.关闭流
out.close();
}
}
3.2 字节输入流-InputStream
InputStream可以将文件中的数据读取出来,该类的定义为:
public abstract class InputStream extends Object implements Closeable
子类实例化使用FileInputStream
常用的方法如下:
public class InputStreamDemo1 {
public static void main(String[] args) throws IOException {
// 1.使用File类找到一个文件
File f = new File("f:" + File.separator + "test.txt");
// 2.实例化输入流对象
InputStream input = new FileInputStream(f);
// 3.读操作
byte[] b = new byte[1024]; //所有的内容读到字节数组中
input.read(b);//读取内容
// 4.关闭流
input.close();
System.out.println("文件内容:" + new String(b) );
}
}
内容输出时含有过多浪费的空间
public class InputStreamDemo2 {
public static void main(String[] args) throws IOException {
// 1.使用File类找到一个文件
File f = new File("f:" + File.separator + "test.txt");
// 2.实例化输入流对象
InputStream input = new FileInputStream(f);
// 3.读操作
byte[] b = new byte[1024]; //所有的内容读到字节数组中
int lenth = input.read(b);//读取内容
// 4.关闭流
input.close();
System.out.println("文件内容:" + new String(b,0,lenth) );
}
}
指定了字节数组空间,可能会造成空间浪费。
public class InputStreamDemo1 {
public static void main(String[] args) throws IOException {
// 1.使用File类找到一个文件
File f = new File("f:" + File.separator + "test.txt");
// 2.实例化输入流对象
InputStream input = new FileInputStream(f);
// 3.读操作
byte[] b = new byte[(int) f.length()]; //数组大小由文件大小决定
int lenth = input.read(b);//读取内容
// 4.关闭流
input.close();
System.out.println("文件内容:" + new String(b) );
}
}
如果按单个字节读取的话:
public class InputStreamDemo1 {
public static void main(String[] args) throws IOException {
// 1.使用File类找到一个文件
File f = new File("f:" + File.separator + "test.txt");
// 2.实例化输入流对象
InputStream input = new FileInputStream(f);
// 3.读操作
byte[] b = new byte[(int) f.length()]; //数组大小由文件大小决定
for (int i = 0; i < b.length; i++) {
b[i] = (byte) input.read();
}
// 4.关闭流
input.close();
System.out.println("文件内容:" + new String(b) );
}
}
当不知道文件大小时,以读取的数据是否为-1作为读完的标志。
public class InputStreamDemo1 {
public static void main(String[] args) throws IOException {
// 1.使用File类找到一个文件
File f = new File("f:" + File.separator + "test.txt");
// 2.实例化输入流对象
InputStream input = new FileInputStream(f);
// 3.读操作
byte[] b = new byte[(int) f.length()]; //数组大小由文件大小决定
int temp = 0;
int len = 0;//接收每一个读取进来的数据
while((temp = input.read()) != -1){
//如果文件还有内容
b[len] = (byte) temp;
len++;
}
// 4.关闭流
input.close();
System.out.println("文件内容:" + new String(b));
}
}
4. 字符流
在程序中,一个字符等于两个字节,针对字符操作的类是字符输出流Writer和字符输入流Reader
4.1 字符输出流-Writer
public abstract class Writer extends Object implements Closeable, Flushable, Appendable
public class WriterDemo1 {
public static void main(String[] args) throws IOException {
//1.使用File类找到一个文件
File f = new File("f:" + File.separator + "test.txt");
//2.实例化输出流对象
Writer out = new FileWriter(f);
//3.写操作
String str = "Hello World!!";
out.write(str);
//4.关闭流
out.close();
}
}
如果要追加内容,且内容换行追加:
public class WriterDemo1 {
public static void main(String[] args) throws IOException {
//1.使用File类找到一个文件
File f = new File("f:" + File.separator + "test.txt");
//2.实例化输出流对象
Writer out = new FileWriter(f,true);
//3.写操作
String str = "\r\nHello World!!";
out.write(str);
//4.关闭流
out.close();
}
}
4.2 字符输入流-Reader
public abstract class Reader extends Object implements Closeable, Readable
public class ReaderDemo1 {
public static void main(String[] args) throws IOException {
// 1.使用File类找到一个文件
File f = new File("f:" + File.separator + "test.txt");
// 2.实例化输入流对象
Reader input = new FileReader(f);
// 3.读操作
char[] c = new char[1024];
int len = input.read(c);
// 4.关闭流
input.close();
System.out.println("文件内容:" + new String(c,0,len));
}
}
public class ReaderDemo1 {
public static void main(String[] args) throws IOException {
// 1.使用File类找到一个文件
File f = new File("f:" + File.separator + "test.txt");
// 2.实例化输入流对象
Reader input = new FileReader(f);
// 3.读操作
char[] c = new char[1024];
int temp = 0;
int len = 0;//接收每一个读取进来的数据
while((temp = input.read()) != -1){
//如果文件还有内容
c[len] = (char) temp;
len++;
}
// 4.关闭流
input.close();
System.out.println("文件内容:" + new String(c));
}
}
5.字节流与字符流的区别
字节流在操作的时候本身不用缓存区的,是与文件直接对接的;而字符流操作时需要缓冲区。
使用字节流时,即使流没有关闭,最终也可以输出到文件;
使用字符流时,所有的内容保存在缓冲区,流关闭时 会强制性的将缓冲区内容写到文件中,如果没有关闭流,文件中就不会有内容输出。
public class WriterDemo1 {
public static void main(String[] args) throws IOException {
//1.使用File类找到一个文件
File f = new File("f:" + File.separator + "test.txt");
//2.实例化输出流对象
Writer out = new FileWriter(f,true);
//3.写操作
String str = "\r\nHello World!!";
out.write(str);
out.flush();//刷新缓冲区内容到文件中
//4.关闭流
// out.close();
}
}
6.范例:文件拷贝
class Copy{
public static void main(String[] args) throws IOException{
if(args.length != 2){
System.out.println("输入的参数不正确!");
System.exit(1);
}
File f1 = new File(args[0]);
File f2 = new File(args[1]);
InputStream input = new FileInputStream(f1);
OutputStream out = new FileOutputStream(f2);
if (input != null && out != null) {
int temp = 0;
while ((temp = input.read()) != -1) {
out.write(temp);
}
System.out.println("拷贝完成!");
input.close();
out.close();
}
}
}
7.总结
-
流的概念
-
字节流与字符流操作文件的基本步骤
3.字节流与字符流的区别
字节流:没有使用缓冲区
字符流:使用缓冲区
4.边读边写的方式在以后开发中非常有用
————————————————
版权声明:本文为CSDN博主「Devin01213」的原创文章,遵循 CC 4.0 BY-SA 版权协议,转载请附上原文出处链接及本声明。
原文链接:https://blog.csdn.net/ym01213/article/details/79702220
来源:CSDN
作者:伍华锋
链接:https://blog.csdn.net/weixin_42030357/article/details/103533769