从零开始的Java开发1-6-4 Java输入输出流:File类绝对路径和相对路径字节流缓冲流字符流对象序列化
Posted karshey
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了从零开始的Java开发1-6-4 Java输入输出流:File类绝对路径和相对路径字节流缓冲流字符流对象序列化相关的知识,希望对你有一定的参考价值。
文章目录
概述
流就是指一连串流动的字符,以先进先出的方式发送信息的通道。
文件输入——读
文件输出——写
File类
文件:可认为是相关记录或放在一起的数据的集合。
在Java中,使用java.io.File
类对文件进行操作。
File类:
构造方法:
常用方法
是否可读或可写:canRead()
和canWrite()
文件是否存在:exists()
获取文件或路径的名称:getName()
是否是目录或文件:isDirectory()
和isFile()
——若文件不存在,false
是否是隐藏文件:isHidden()
返回文件的最后一次修改时间:lastModified()
创建目录/创建多级目录:mkdir()
/mkdirs()
File类的常用方法
我在C盘有一个文件夹temp,里面有一个txt文件名为score。
则它在Windows下的路径为:c:\\\\temp\\\\score.txt
。(一个\\是转义字符)
代码1:
- 构造函数
isFile()
和isDirectory()
public class FileDemo
public static void main(String[] args)
// 创建File对象
File file = new File("c:\\\\temp\\\\score.txt");
// 判断是否文件or目录
boolean flag1 = file.isFile();
boolean flag2 = file.isDirectory();
System.out.println("是否是文件:" + flag1);
System.out.println("是否是目录:" + flag2);
输出:
是否是文件:true
是否是目录:false
也可以这样:
File file=new File("c:\\\\temp","score.txt");
或
File file1=new File("c:\\\\temp");
File file=new File(file1,"score.txt");
代码2:
exists()
:判断文件是否存在mkdir()
:创建文件目录
// 创建一个目录
File file2 = new File("c:\\\\temp", "HashSet");
// 判断这个文件是否存在
if (!file2.exists())
file2.mkdir();
运行后:
如果想创建多级目录:(先把HashSet删掉)
// 创建多级目录
File file2 = new File("c:\\\\temp\\\\tempp\\\\HashSet", "HashSet");
// 判断这个文件是否存在
if (!file2.exists())
file2.mkdirs();
运行后:
代码3:
创建文件:
createNewFile()
:创建文件
// 创建文件
File file = new File("c:\\\\temp\\\\score1.txt");
if (!file.exists())
try
file.createNewFile();
catch (IOException e)
// TODO Auto-generated catch block
e.printStackTrace();
运行:
ps:若代码3中参数路径为:"c:\\\\temp\\\\score1"
,则会创建一个没有拓展名的文件。
绝对路径和相对路径
- 绝对路径:从盘符开始的路径
- 相对路径:从当前路径开始的路径
假设这是当前位置:
它的绝对路径是:c:\\\\temp\\\\tempp\\\\1.txt
因为现在就在tempp这个文件夹下,所以1.txt
的相对目录是:1.txt
tempp
的上级目录如下:
想在以temp
为当前位置的位置找到1.txt
,相对路径为:tempp\\\\1.txt
访问上一层目录的方法:..\\\\
访问上两层:..\\\\..\\\\
在Eclipse下:
执行代码:
//创建文件
File f=new File("temp.txt");
try
f.createNewFile();
catch (IOException e)
// TODO Auto-generated catch block
e.printStackTrace();
会在工程目录下出现一个temp.txt
判断一个路径是绝对路径还是相对路径: isAbsolute()
:若是绝对路径,则返回true
获取路径
getPah()
:获得File构造方法参数表示的路径,也就是内容与File构造方法参数一致getAbsolutePath()
:获取绝对路径
代码:
File f=new File("temp.txt");
try
f.createNewFile();
//是否绝对路径
System.out.println(f.isAbsolute());
//获取相对路径
System.out.println(f.getPath());
//获取绝对路径
System.out.println(f.getAbsolutePath());
//获取文件名
System.out.println(f.getName());
catch (IOException e)
// TODO Auto-generated catch block
e.printStackTrace();
输出:
false
temp.txt
D:\\eclipse\\allProj\\temp.txt
temp.txt
字节流概述
- 字节输入流
InputStream
- 字节输出流
OutputStream
字节输入流InputStream
包括:
- 文件输入流
FileInputStream
- 管道输入流
PipedInputStream
- 过滤器输入流
FilterInputStream
- 对象输入流
ObjectInputStream
- 顺序输入流
SequenceInputStream
- 字节数组输入流
ByteArrayInputStream
- 缓冲字符输入流
StringBufferInputStream
过滤器输入流FilterInputStream
包括:
- 回压输入流
PushbackInputStream
- 缓冲输入流
BufferedInputStream
- 数据输入流
DataInputStream
字节输出流OutputStream
包括:
- 文件输出流
FileOutputStream
- 管道输出流
PipedOutputStream
- 过滤器输出流
FilterOutputStream
- 对象输出流
ObjectOutputStream
- 字节数组输出流
ByteArrayOutputStream
过滤器输出流FilterOutputStream
包括:
- 格式化输出流
PrintStream
- 缓冲输出流
BufferedOutputStream
- 数据输出流
DataOutputStream
文件输入流 FileInputStream
- 从文件系统中的某个文件中获取输入字节
- 用于读取诸如图像数据之类的原始字节流
文档如下:
构造方法
重要方法
方法名 | 描述 |
---|---|
public int read() | 从输入流中读取一个数据字节 |
public int read(byte[] b) | 从输入流中将最多b.length个字节的数据读入一个byte数组中 |
public int read(byte[] b,int off,int len) | 从输入流中将最多len个字节的数据读入一个byte数组中 |
public int close() | 关闭此文件输入流并释放与此流有关的所有系统资源 |
若返回值为-1,则表达已经达到文件末尾。
代码演示:
我们在工程目录下有一个temp.txt
文件:我们想要读取它。
代码(无参的read()
):
public static void main(String[] args)
try
// 创建一个FileInputStream对象:要捕获FileNotFoundException异常
FileInputStream fis = new FileInputStream("temp.txt");
// 读取文件内容read:要捕获IOException异常
int n;
while ((n = fis.read()) != -1)
System.out.print((char) n);
fis.close();// 关闭输入流,释放资源
catch (FileNotFoundException e)
e.printStackTrace();
catch (IOException e) // IOException是FileNotFoundException的父类
e.printStackTrace();
输出:asd123345
核心代码:
int n;
while ((n = fis.read()) != -1)
System.out.print((char) n);
也可以是这样(但是重复了):
int n = fis.read();
while (n != -1)
System.out.print((char) n);
n = fis.read();
int read(byte[] b)
的代码——把核心代码替换成:
//读取数据,存放到一个byte类型的数组中
byte[] b=new byte[100];
fis.read(b);
System.out.println(new String(b));
fis.close();
输出:asd123345
若把fis.read(b);
改成fis.read(b,0,6);
,则输出:asd123
第二个参数表示偏移量:从byte数组的第几个开始存数据。
第三个参数表示要读取的字符个数。
若第二个参数改为1,则输出: asd123
,前面空了一格。
文件输出流 FileOutputStream
用来将数据写入到文件中。
构造方法:
重要方法
方法名 | 描述 |
---|---|
public void write(int b) | 将指定字节写入文件输出流 |
public void write(byte[] b) | 将b.length个字节从byte数组写入文件输出流 |
public void write(byte[] b,int off,int len) | 将指定byte数组中从偏移量off开始的len个字节写入文件输出流 |
public void close() | 关闭此文件输出流并释放与此流有关的所有系统资源 |
代码:
public class FileOutputDemo
public static void main(String[] args)
FileOutputStream fos;
FileInputStream fis;
try
fos = new FileOutputStream("temp.txt");
fis = new FileInputStream("temp.txt");
//写入文件
fos.write(51);
fos.write('a');
//读取写入的文件
System.out.print(fis.read());
System.out.print((char) fis.read());
fis.close();
fos.close();
catch (FileNotFoundException e)
e.printStackTrace();
catch (IOException e)
e.printStackTrace();
输出:51a
文件:因为编码原因,显示会不一样,但由输出我们可以知道写入的就是我们想要的51a
如果把fos = new FileOutputStream("temp.txt");
改成fos = new FileOutputStream("temp.txt",true);
,再运行一次,则文件内容为:3a3a
。
原因:
FileOutputStream(File file, boolean append)
Creates a file output stream to write to the file represented by the specified File object.
由上述例子可知,文件输入输出流是不太适合做和字符相关的工作的。
我们再来看一个文件拷贝的例子。我们在工程目录下有一个jpg文件a,我们想把它拷贝到a_copy上。
复制粘贴其实就是读取和写入。
代码:
public static void main(String[] args)
try
// 文件拷贝
FileInputStream fis = new FileInputStream("a.jpg");
FileOutputStream fos = new FileOutputStream("a_copy.jpg");
int n = 0;// 存储read方法的返回值
byte[] b = new byte[1024];//一次读1024个字节
while ((n = fis.read(b)) != -1)
fos.write(b);
fis.close();
fos.close();
catch (FileNotFoundException e)
e.printStackTrace();
catch (IOException e)
e.printStackTrace();
运行后:
注意:fos.write(b,0,n);
可以保证拷贝后的文件大小一致——因为副本文件可能比原来的文件大,这是由一次拷贝b个字节造成的(剩下的文件字节小于b个时,就会使得拷贝后的文件大一点)
缓冲流概述
- 缓冲输入流:
BufferedInputStream
- 缓冲输出流:
BufferedOutputStream
缓冲输入流相关方法:
缓冲输出流相关方法:
缓冲区满了会自动触发write()方法。
案例:缓冲输入输出流
flush()
:清空缓冲区数据,使之触发write()
方法
代码(注释很详细):
public class BufferedDemo1
public static void main(String[] args)
try
FileOutputStream fos = new FileOutputStream("temp.txt");
BufferedOutputStream bos = new BufferedOutputStream(fos);
FileInputStream fis = new FileInputStream("temp.txt");
BufferedInputStream bis = new BufferedInputStream(fis);
// 写
bos.write(50);
bos.write('a');
// 运行,发现temp.txt是空的,说明数据还在缓冲区里
// 缓冲区未满,没有触发自动write操作
// 强制清空,会触发写操作
bos.flush();
// 运行后,temp.txt就有2a了
// 读取
System.out.println(bis.read());
System.out.println((char) bis.read());
// 实际上,关闭缓冲区也会触发写操作
bos.close();
// 关闭所有流
bis.close();
fis.close();
fos.close();
catch (FileNotFoundException e)
e.printStackTrace();
catch (IOException e)
e.printStackTrace();
文件内容:2a
输出:
50
a
字符流概述
- 字符输入流
Reader
- 字符输出流
Writer
字符输入流:
字符输出流:
案例:字节字符转换流
InputStreamReader
OutputStreamReader
相关方法:
代码演示:
输入流:我们想读取文件如下:
代码:两个方法都可以
public static void main(String[] args)
try
FileInputStream fis = new FileInputStream("temp.txt");
InputStreamReader isr = new InputStreamReader(fis);
// 读取数据
// 方法1
int n = 0;
char[] c = new char[10];
while ((n = isr.read()) != -1)
System.out.print((char) n);
// 方法2
int n1 = 0;
while ((n1 = isr.read(c)) != -1)
String str = new String(c, 0, n1);// n1表示要转换实际存储的字符数量
System.out.print(str);
catch (FileNotFoundException e)
e.printStackTrace();
catch (IOException e)
e.printStackTrace();
输出:
123
asdzxc
fgh
输出流:
我们想把temp.txt的内容读出来,然后写到tempp.txt中。
代码:
public class ReaderDemo
public static void main(String[] args)
try
FileInputStream fis = new FileInputStream("temp.txt");
InputStreamReader isr = new InputStreamReader(fis);
FileOutputStream fos = new FileOutputStream("tempp.txt");
OutputStreamWriter osw = new OutputStreamWriter(fos);
// 读取数据
char[] c = new char[10];
int n1 = 0;
while ((n1 = isr.read(c)) != -1)
// 写字符串
String str = new String(c, 0, n1);// n1表示要转换实际存储的字符数量
osw.write(str);
// 或者写字符数组
// osw.write(c,0,n1);
// 清空缓存
osw.flush();
// 关闭流
fis.close();
fos.close();
isr.close();
osw.close();
catch (FileNotFoundException e)
e.printStackTrace();
catch (IOException e)
e.printStackTrace();
运行后:
关于编码:输入输出的编码要相同,不然会乱码。
构造函数中,String charsetName
是字符集,在这里可以写想要的编码形式,如"GBK"
,"UTF-8"
InputStreamReader(InputStream in, String charsetName)
Creates an InputStreamReader that uses the named charset.
OutputStreamWriter(OutputStream out, String charsetName)
Creates an OutputStreamWriter that uses the named charset.
其他字符流
代码:
public static void main(String[] args)
try
FileInputStream fis = new FileInputStream("temp.txt");
InputStreamReader isr = new InputStreamReader(fis, "GBK");
BufferedReader br = 以上是关于从零开始的Java开发1-6-4 Java输入输出流:File类绝对路径和相对路径字节流缓冲流字符流对象序列化的主要内容,如果未能解决你的问题,请参考以下文章