Java 基础-IO、stream 流、文件操作
输入输出流的分类
在 java.io
包中,包含了输入输出操作所需的类。
I/O 流可以安装不同的标准分类:
- 按照流的方向分类:
- 输入流:将信息从代码外部输入代码
- 输出流:将代码得到的数据输出到文件、网络、内存等地方
- 按照流的分工分类:
- 节点流:访问磁盘、网络等获取数据的流,可以直接实例化
- 处理流:对信息进行加工转换的流,需要基于节点流实例化
- 按处理数据的类型分类:
- 面向字符的流:处理字符数据,自动实现 Java 内部格式(16 bit char 类型)与外部格式(UTF-8 等)的转换。基类是 Reader 和 Writer
- 面向字节的流:处理一般数据,基类是 InputStream 和 OutputStream
输入输出流
字符流
字符输入流 Reader
所有的字符输入流都继承自 Reader 类。
常用的字符输入流有:BufferedReader、InputStreamReader、FilterReader、StringReader、PipedReader、CharArrayReader。
字符输出流 Writer
所有的字符输出流都继承自 Writer 类。
常用的字符输出流有:BufferedWriter、OutputStreamWriter、FilterWriter、StringWriter、PipedWriter、CharArrayWriter。
字节流
字节输入流 InputStream
所有的字节输入流都继承自 Writer 类。
常用的字节输入流有:FileInputStream、FilterInputStream(子类 BufferedInputStream)、ByteArrayInputStream。
字节输出流 OutputStream
所有的字节输出流都继承自 Writer 类。
常用的字节输出流有:FileOutputStream、FilterOutputStream(子类 BufferedOutputStream)、ByteArrayOutputStream。
常用的输入输出流
FileInputStream 和 FileOutputStream
这两个类用于按字节读写文件。
FileInputStream 从文件读取字节数据
可以用用字符串类型的文件名或文件对象创建 FileInputStream 类的对象。
- 使用字符串类型的文件名创建输入流对象读取文件:
InputStream f = new FileInputStream("C:/java/hello");
- 使用文件对象来创建输入流对象读取文件。首先得使用 File() 方法来创建一个文件对象:
File f = new File("C:/java/hello");
InputStream out = new FileInputStream(f);
FileInputStream 对象的常用方法:
方法名 | 描述 |
---|---|
public void close() throws IOException{} | 关闭此文件输入流并释放与此流有关的所有系统资源 |
protected void finalize()throws IOException {} | 清除与该文件的连接。确保在不再引用文件输入流时调用其 close 方法 |
public int read()throws IOException{} | 从 InputStream 对象读取一个字节的数据。返回为整数值。如果已经到结尾则返回-1。 |
public int read(byte[] r) throws IOException{} | 从输入流读取r.length长度的字节。返回读取的字节数。如果是文件结尾则返回-1。 |
public int available() throws IOException{} | 返回下一次对此输入流调用的方法可以不受阻塞地从此输入流读取的字节数。返回一个整数值。 |
FileOutputStream 向文件写字节数据
如果文件不存在,FileOutputStream 会先创建文件。
- 使用字符串类型的文件名来创建一个输出流对象:
OutputStream f = new FileOutputStream("C:/java/hello")
- 使用一个文件对象来创建一个输出流来写文件。我们首先得使用File()方法来创建一个文件对象:
File f = new File("C:/java/hello");
OutputStream f = new FileOutputStream(f);
FileOutputStream 对象的常用方法:
方法名 | 描述 |
---|---|
public void close() throws IOException{} | 关闭此文件输入流并释放与此流有关的所有系统资源。抛出IOException异常。 |
protected void finalize()throws IOException {} | 这个方法清除与该文件的连接。确保在不再引用文件输入流时调用其 close 方法。抛出IOException异常。 |
public void write(int w)throws IOException{} | 把指定的字节写到输出流中。注意一次只能写一字节 |
public void write(byte[] w) | 把指定数组中w.length长度的字节写到OutputStream中。 |
示例
import java.io.*;
public class StreamTest {
public static void main(String[] args) {
try {
byte [] arr = {'h', 'e', 'l', 'l', 'o', ' ', 'w', 'o', 'r'};
OutputStream os = new FileOutputStream("test.txt");
for (byte i : arr) {
os.write(i); // 写一个字节到文件
}
os.write(arr); // 写字节数组到文件
os.close();
File f = new File("test.txt");
InputStream is = new FileInputStream(f);
System.out.println(is.read()); // 显示 104
byte [] arr2 = new byte[10];
is.read(arr2);
for (byte i : arr2) {
System.out.print((char)i);
}
is.close();
is = new FileInputStream(f);
int size = is.available();
for (int i = 0; i < size; i++) {
System.out.print((char)(is.read()));
}
} catch (IOException e) {
System.out.println(e);
}
}
}
上面程序的输出为:
104
ello worhehello worhello wor
文件 test.txt 内容为:
hello worhello wor
OutputStreamWriter 和 InputStreamReader
这两个类用于转换字节流和字符流。
OutputStreamWriter
OutputStreamWriter 是将字符流转为字节流的桥梁,可以用指定的编码将字符编码为字节。可以在构造方法中指定字符集,或者默认用操作系统字符集。
使用字符串类型的文件名来创建一个输出流对象:
OutputStreamWriter osw = new OutputStreamWriter(OutputStream out, CharsetEncoder enc)
OutputStreamWriter 对象的常用方法:
方法名 | 描述 |
---|---|
void close() | 关闭流,关闭之前会自动清空 |
void flush() | 清空流 |
String getEncoding() | 返回当前流的字符编码 |
void write(char[] cbuf, int off, int len) | 写入字符数组的一部分 |
void write(int c) | 写入一个字符 |
void write(String str, int off, int len) | 写入字符串的一部分 |
InputStreamReader
将字节流转为字符流。读取字节并按照指定的字符集解码为字符。
InputStreamReader(InputStream in, Charset cs)
FileOutputStream 对象的常用方法:
方法名 | 描述 |
---|---|
void close() | 关闭流并释放相关的系统资源 |
String getEncoding() | 返回当前流使用的字符集编码 |
int read() | 读一个字符 |
int read(char[] cbuf, int offset, int length) | 将字符读到数组的指定部分 |
boolean ready() | 表示当前流是否就绪,可以随时读数据 |
示例
import java.io.*;
public class StreamTrans {
public static void main(String[] args) throws IOException {
InputStream is = new FileInputStream("test.txt");
InputStreamReader isr = new InputStreamReader(is);
char[] arr = new char[10];
isr.read(arr);
System.out.println(arr);
isr.close();
}
}
FileReader 和 FileWriter
用于按字符读写文件。跟 FileInputStream 和 FileOutputStream 类似。
BufferedReader 和 BufferedWriter
这两个类可以为 I/O 操作提供缓冲区,实现单个字符、数组和字符串的读写。
BufferedReader
继承自 Reader。
比 FileReader 类多了个 readLine()
方法,可以一次读取完整的一行(跨平台)。
BufferedWriter
BufferedWriter 有个跨平台的 newLine()
方法,可以在各个平台实现统一的换行效果。
示例
import java.io.*;
public class BufferedTest {
public static void main(String[] args) {
try {
BufferedWriter bw = new BufferedWriter(new FileWriter("test.txt"));
bw.newLine();
bw.write("hehe");
bw.newLine();
bw.write("hehe");
bw.flush();
BufferedReader br = new BufferedReader(new FileReader("test.txt"));
String line = br.readLine();
while (line != null) {
System.out.println(line);
line = br.readLine();
}
} catch (IOException e) {
System.out.println(e);
}
}
}
输出:
hehe
hehe
DataOutputStream 和 DataInputStream
这两个类具有写各种基本数据类型的方法,且各种类型可以跨平台。另外,可以用 size()
方法统计写入的字节数。
DataOutputStream
常用方法:
方法 | 描述 |
---|---|
void flush() | Flushes this data output stream. |
int size() | 返回当前计数器的值,目前已经写入这个流的字节数 |
void write(byte[] b, int off, int len) | 从指定的字节数组 off 偏移处,写 len 个字节到输出流 |
void write(int b) | 写入指定的字节(参数 b 的低8位)到输出流 |
void writeBoolean(boolean v) | 将布尔数据作为1字节的值写到输出流 |
void writeByte(int v) | 将字节数据作为1字节的值写到输出流 |
void writeBytes(String s) | 将字符串作为字节序列写到输出流 |
void writeChar(int v) | 将字符数据作为2字节的值写到输出流,高位在前 |
void writeChars(String s) | 将字符串作为字符序列写到输出流 |
void writeDouble(double v) | 通过 Double 类中的 doubleToLongBits 方法将double类型参数转为long 类型后,将其完整的8字节写入输出流,高字节在前 |
void writeFloat(float v) | |
void writeInt(int v) | |
void writeLong(long v) | |
void writeShort(int v) | |
void writeUTF(String str) |
DataInputStream
可以按照指定的类型读取数据。
示例
import java.io.*;
public class DataStream {
public static void main(String[] args) throws IOException {
DataOutputStream dos = new DataOutputStream(new FileOutputStream("test.txt"));
dos.writeInt(666);
dos.writeBoolean(false);
dos.writeChars("hello world");
dos.flush();
System.out.println(dos.size()); // 总字节数
DataInputStream dis = new DataInputStream(new FileInputStream("test.txt"));
System.out.println(dis.readInt()); // 读整型数据
System.out.println(dis.readBoolean());
System.out.println(dis.readByte());
}
}
标准输入输出流
System 类的静态成员变量,包括:
- System.in:InputStream 类型的标准输入流,默认是键盘
- System.out:PrintStream 类型的标准输出流,默认是显示器
- System.err:PrintStream 类型的标准错误输出流,默认也是输出到显示器
按类型输入输出数据
- printf 方法格式化输出,其中多了
%n
这个平台无关的换行标志 - Scanner 类从标准输入流获取指定类型的输入,支持 nextLine()、nextByte() 等方法:
Scanner s = new Scanner(System.in);
int i = s.nextInt();
标准输入输出流重定向
可以将标准流重定向到文件,这样在使用标准输出流时,实际使用的就是文件了。
InputStream in = new BufferedInputStream(new FileInputStream("test.txt"));
OutputStream out = new BufferedOutputStream(new FileOutputStream("out.txt"));
System.setIn(in);
System.setOut(out);
System.setErr(out);
File 类
File 类提供了文件的相关操作,包括:
- 创建、删除、重命名文件
- 判断文件是否存在
- 判断文件的读写权限
- 设置和查询文件的最新修改时间
import java.io.*;
public class FileTest {
public static void main(String[] args) {
File f = new File("test.txt");
if (f.exists()) { // 判断文件或目录是否存在
f.delete(); // 删除文件或目录
} else {
try {
f.createNewFile(); // 创建文件
} catch (Exception e) {
System.out.println(e);
}
}
}
}
对象序列化
如果需要在程序结束时保存对象的信息,可以将对象序列化后保存到磁盘上。前提是对象已经实现了 Serializable 接口:
- ObjectOutputStream 可以用 writeObject 方法把对象写入磁盘
- ObjectInputStream 可以用 readObject 方法把对象读入程序
对于序列化时不想保存的属性,可以加 transient 修饰。另外 static 类型的变量,不属于任何一个对象,所以也不会序列化。
RandomAccessFile 类
Java 把输入输出都当做字节流处理,所以对随机的文件读写支持的不太好。
- 可跳转到文件的任意位置读写
- RandomAccessFile 类实现了 DataInput 和 DataOutput 接口,可以使用普通读写方法
Java 基础-IO、stream 流、文件操作的更多相关文章
- Java基础-IO流对象之字节流(Stream)
Java基础-IO流对象之字节流(Stream) 作者:尹正杰 版权声明:原创作品,谢绝转载!否则将追究法律责任. 在前面我分享的笔记中,我们一直都是在操作文件或者文件夹,并没有给文件中写任何数据.现 ...
- Java基础-IO流对象之随机访问文件(RandomAccessFile)
Java基础-IO流对象之随机访问文件(RandomAccessFile) 作者:尹正杰 版权声明:原创作品,谢绝转载!否则将追究法律责任. 一.RandomAccessFile简介 此类的实例支持对 ...
- Java基础-IO流对象之内存操作流(ByteArrayOutputStream与ByteArrayInputStream)
Java基础-IO流对象之内存操作流(ByteArrayOutputStream与ByteArrayInputStream) 作者:尹正杰 版权声明:原创作品,谢绝转载!否则将追究法律责任. 一.内存 ...
- Java基础IO流(二)字节流小案例
JAVA基础IO流(一)https://www.cnblogs.com/deepSleeping/p/9693601.html ①读取指定文件内容,按照16进制输出到控制台 其中,Integer.to ...
- Java基础-IO流对象之序列化(ObjectOutputStream)与反序列化(ObjectInputStream)
Java基础-IO流对象之序列化(ObjectOutputStream)与反序列化(ObjectInputStream) 作者:尹正杰 版权声明:原创作品,谢绝转载!否则将追究法律责任. 一.对象的序 ...
- Java基础-IO流对象之字符缓冲流(BufferedWriter与BufferedReader)
Java基础-IO流对象之字符缓冲流(BufferedWriter与BufferedReader) 作者:尹正杰 版权声明:原创作品,谢绝转载!否则将追究法律责任. 一.字符缓冲流 字符缓冲流根据流的 ...
- Java基础-IO流对象之字节缓冲流(BufferedOutputStream与BufferedInputStream)
Java基础-IO流对象之字节缓冲流(BufferedOutputStream与BufferedInputStream) 作者:尹正杰 版权声明:原创作品,谢绝转载!否则将追究法律责任. 在我们学习字 ...
- Java基础-IO流对象之转换流(InputStreamReader与OutoutStreamWriter)
Java基础-IO流对象之转换流(InputStreamReader与OutoutStreamWriter) 作者:尹正杰 版权声明:原创作品,谢绝转载!否则将追究法律责任. 一.转换流概述 我们之前 ...
- Java基础-IO流对象之File类
Java基础-IO流对象之File类 作者:尹正杰 版权声明:原创作品,谢绝转载!否则将追究法律责任. 一.IO技术概述 回想之前写过的程序,数据都是在内存中,一旦程序运行结束,这些数据都没有了,等下 ...
- 《Java基础——IO流》
Java基础--IO流 一.字节流: 1.输入流 (InputStream) 规则: 此处用于读取txt文件中的内容. 代码: import java.io.*; public c ...
随机推荐
- C语言scanf的返回值
#include <stdio.h> int main(void) { long num; long sum = 0L; int status; printf("Please e ...
- #include <xxx.h>和#include "xxx.h"的区别
<>代表在系统目录下查找该头文件(系统定义头文件) ""代表在用户目录下查找该头文件(自定义头文件)
- PAT Advanced 1035 Password (20 分)
To prepare for PAT, the judge sometimes has to generate random passwords for the users. The problem ...
- VMmare下安装redhat
一.虚拟机必须安装在自定义的文件夹下,虚拟硬盘文件必须存放在自定义路径下(避免中文) 二.安装时选择linux类型时必须选择red hat enterprise linux 5 64位 三.操作系统名 ...
- 【开车旅行】题解(NOIP2012提高组)
分析 首先我们可以发现,两个询问都可以通过一个子程序来求. 接着,如果每到一个城市再找下一个城市,显然是行不通的.所以首先先预处理从每一个城市开始,小A和小B要去的城市.预处理的方法很多,我用的是双向 ...
- 关闭DELPHI 欢迎页
打开注册表 HKEY_CURRENT_USER\Software\Embarcadero\BDS\20.0\Known IDE Packages(20.0为版本号) 将$(BDS)\Bin\start ...
- linux运维、架构之路-nfs网络文件系统
一.nfs介绍 NFS是Network File System的缩写,是网络文件系统,它的主要功能是通过网络(一般是局域网)让不同的主机系统之间可以共享文件或目录,主要存储用户上传的图片附件等信息. ...
- css语法以及css选择器
CSS语法 CSS的标准语法主要由两方面构成一是 选择器.二是 声明框. 一.选择器 通过选择器可以选定页面指定的元素,并将声明块中的样式应用在选择器选中的元素中去. 二.声明框 ...
- mysql Update语句 语法
mysql Update语句 语法 作用:用于修改表中的数据.广州大理石机械构件 语法:UPDATE 表名称 SET 列名称 = 新值 WHERE 列名称 = 某值 mysql Update语句 示例 ...
- 前端js怎么实现大文件G级的断点续传(分块上传)和分段下载
需求: 支持大文件批量上传(20G)和下载,同时需要保证上传期间用户电脑不出现卡死等体验: 内网百兆网络上传速度为12MB/S 服务器内存占用低 支持文件夹上传,文件夹中的文件数量达到1万个以上,且包 ...