1.Flie类
1.1概述:
在学习IO流之前,我们先学习一个相关的类:File类。
文件和目录路径名的抽象表示形式
1.2构造方法:
public File(String pathname)//根据一个路径,得到File对象
public File(String parent,String child) //根据一个目录和一个子文件/目录得到一个File对象
public File(File parent,String child) //根据一个父File对象和一个子文件/目录得到File对象
1.2.1代码案例:
public class FileTest {
public static void main(String[] args) {
//public File(String pathname)//根据一个路径,得到File对象,建议使用第一种
File file = new File("D:\\java.txt");
//public File(String parent,String child) //根据一个目录和一个子文件/目录得到一个File对象
File file1 = new File("D","java.txt");
//public File(File parent,String child) //根据一个父File对象和一个子文件/目录得到File对象
File file2 = new File("D");
File file3 = new File(file2,"java.txt");
}
}
1.3创建文件:
①创建一个新的空文件
public boolean createNewFile() throws IOException
如果指定的文件不存在并成功地创建,则返回 true;如果指定的文件已经存在,则返回 false
②创建一个单级文件夹
public boolean mkdir()
此方法只能创建单级目录,如果路径是多级的,必须确保上级已经存在
③创建一个多级文件夹
public boolean mkdirs()
创建一个多级文件夹
1.3.1 代码案例:
/**
* 创建文件
*/
public class FileTest {
public static void main(String[] args) throws IOException {
// File file = new File("D:\\1.txt");
// //创建文件
// System.out.println(file.createNewFile());
// //创建文件夹
// File file2 = new File("D:\\test");
// System.out.println(file2.mkdir());
// File file3 = new File("D:\\test.txt");//文件夹名字为test.txt
// System.out.println(file3.mkdir());
// File file1 = new File("1.txt");//忘记带盘符,则直接在java中根目录下创建
// System.out.println(file1.createNewFile());
File file = new File("test\\test\\test");//错误
System.out.println(file.mkdir());
}
}
1.4删除文件:
1.4.1概述:
public boolean delete()
删除此抽象路径名表示的文件或目录。如果此路径名表示一个目录,则该目录必须为空才能删除
1.4.2代码案例:
/**
* 删除功能
*/
public class FileTest {
public static void main(String[] args) throws IOException {
File file = new File("D:\\1.txt");
System.out.println(file.createNewFile());
file.delete();//删除文件
}
}
1.4.3注意:
1.java删除文件不进回收站
2.删除一个文件夹时,优先保证它为空
3.创建文件对象时,如果不写盘符,则创建文件或文件夹时会相对于工程目录去创建
1.5重命名文件:
1.5.1概述:
public boolean renameTo(File dest)
重新命名此抽象路径名表示的文件。
1.5.2注意:
如果路径相同,该方法为重命名功能
如果路径不同,则该方法重命名+剪贴到指定路径下
1.5.3代码案例:
/**
* 重命名功能 转移功能
*/
public class FileTest {
public static void main(String[] args) throws IOException {
// File file = new File("D:\\1.txt");
// System.out.println(file.createNewFile());
// File newFile = new File("D:\\2.txt");
// System.out.println(file.renameTo(newFile));
File file = new File("1.txt");//转移路径
System.out.println(file.createNewFile());
File newFile = new File("D:\\2.txt");
System.out.println(file.renameTo(newFile));
}
}
1.6判断文件:
①测试此抽象路径名表示的文件是否是一个目录。
public boolean isDirectory()
②测试此抽象路径名表示的文件是否是一个标准文件。
public boolean isFile()
③测试此抽象路径名指定的文件是否是一个隐藏文件。
public boolean isHidden()
④测试此抽象路径名表示的文件或目录是否存在。
public boolean exists()
⑤测试应用程序是否可以读取此抽象路径名表示的文件。
public boolean canRead()
⑥测试应用程序是否可以修改此抽象路径名表示的文件。
public boolean canWrite()
1.6.1代码案例:
/**
* 判断功能
*/
public class FileTest {
public static void main(String[] args) throws IOException {
File file = new File("D:\\1.txt");
File file2 = new File("D:\\test");
System.out.println(file.createNewFile());
System.out.println(file2.mkdir());
//判断是否为文件夹
System.out.println(file.isDirectory());
System.out.println(file2.isDirectory());
//判断是否为文件
System.out.println(file.isFile());
//判断是否可读、隐藏
System.out.println(file2.isHidden());
System.out.println(file.canRead());
//判断是否存在
System.out.println(file.exists());
}
}
1.7获取功能:
①public String getName()
返回由此抽象路径名表示的文件或目录的名称。
②public String getAbsolutePath()
返回此抽象路径名的绝对路径名字符串。
③public String getPath()
将此抽象路径名转换为一个路径名字符串。
④public long length()
返回由此抽象路径名表示的文件的长度。如果此路径名表示一个目录,则返回值是不确定的。
⑤public long lastModified()
返回此抽象路径名表示的文件最后一次被修改的时间。
1.7.1代码案例:
/**
* 获取功能
*/
public class FileTest {
public static void main(String[] args) throws IOException {
File file = new File("D:\\1.txt");
file.createNewFile();
System.out.println(file.getName());//获取名字
System.out.println(file.length());//获取长度,返回的是内容的字节长度,若无内容则为0
System.out.println(file.getAbsolutePath());//抽象的绝对地址
System.out.println(file.getPath());//相对路径
System.out.println(file.lastModified());//返回最后一次被修改的时间,毫秒计时
Date date = new Date(file.lastModified());
SimpleDateFormat simpleDateFormat = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");
String s = simpleDateFormat.format(date);
System.out.println(s);
}
}
1.8高级获取功能:
①public String[] list()
获取指定目录下所有文件和文件夹的名称数组的方法
②public File[] listFiles()
返回一个抽象路径名数组,这些路径名表示此抽象路径名表示的目录中的文件。
1.8.1代码案例:
/**
* File高级获取
*/
public class FileTest{
public static void main(String[] args) {
File file= new File("D:\\start");
String [] list = file.list();
for(String s:list){
System.out.println(s);
}
File[] files =file.listFiles();
for(File file1:files){
System.out.println(file1.getName());
}
}
}
1.8.2练习:
/**
* 获取指定路径下所有已txt结尾的文件,并输出
*/
public class FileWork{
public static void main(String[] args) {
File file = new File("D:\\start");
String[] list = file.list(new FilenameFilter() {
@Override
public boolean accept(File dir, String name) {
File file1 = new File(dir, name);
boolean flag = file1.isFile();
boolean flag2 = file1.getName().endsWith(".txt");
return flag && flag2;
}
});
for(String s:list){
System.out.println(s);
}
}
}
2.IO 流
2.1概述:
IO流又叫做输入输出流
当我们将内存中的数据写到硬盘上时,这个过程叫“输出流”(Output)
当我们将硬盘上的数据读取到内存中,这个过程叫“输入流”(Input)
流是一个抽象的概念,是对数据传输的总称,也就是说数据在设备间的传输,叫做流。
2.2分类:
2.2.1按照数据流向:
输入流
输出流
2.2.2按照数据类型:
字节流:
字符流:为了方便表示某些数据,就出现了字符流
2.2.3如果使用?
如果你在电脑自带的笔记本打开文件,能看懂的话,就用字符流,否则就用字节流
如果你什么都不知道,就要字节流
2.3字节流:
2.3.1字节输出流:
OutputStream:此抽象类是表示输出字节流的所有类的超类。
2.3.1.1构造方法:
/*
*学习FileOutputStream:
* 构造方法:
* FileOutputStream(File file)
* FileOutputStream(String name)
*/
public class FileOutputStreamDemo {
public static void main(String[] args) throws FileNotFoundException {
//方法1
// File file = new File("D:\\a.txt");
// FileOutputStream fos = new FileOutputStream(file);//抛出一个异常
// 方法2
FileOutputStream fos = new FileOutputStream("D:\\a.txt");
}
}
2.3.1.2写入数据:
/**
* 在一个文件中写入Hello world!
*字节流写数据的方式:
*
* public void write(int b) throws IOException
* 将指定字节写入此文件输出流。
*
* public void write(byte[] b) throws IOException
* 将 b.length 个字节从指定 byte 数组写入此文件输出流中。
*
* public void write(byte[] b,int off,int len) throws IOException
* 将指定 byte 数组中从偏移量 off 开始的 len 个字节写入此文件输出流。
*
*/
public class FileOutputStreamDemo2 {
public static void main(String[] args) throws IOException {
FileOutputStream fos = new FileOutputStream("D:\\a.txt");
//实现写数据操作
//fos.write("hello world".getBytes());
//fos.write(97);//写入字节码,97-a
byte [] bytes ={
97,98,99,100,101};
//fos.write(bytes);
fos.write(bytes,1,4);
//关闭流
fos.close();
}
}
2.3.1.3注意事项:
①创建字节输出流到底做了哪些事情?
答:首先调用系统功能去创建文件,创建fos对象,将fos对象指向了我们创建的文件。
②数据写成功后,为什么一定要写close()
答:让流对象变成垃圾,以便垃圾回收器回收。同时通知系统去释放该文件相关的资源。
③如果实现数据的换行?
添加换行符
public class FileOutputStreamDemo3 {
public static void main(String[] args) throws IOException {
FileOutputStream fos = new FileOutputStream("D:\\1.txt");
for(int i = 0;i<10;i++){
fos.write(("hello world"+i).getBytes());
fos.write("\n".getBytes());
}
}
}
④如果实现数据的追加写入?
//public FileOutputStream(String name, boolean append)
FileOutputStream fos = new FileOutputStream("D:\\1.txt",true);
//代码还是上述代码,只需要追加true。
2.3.1.4异常处理:
public class FileOutputStreamDemo4 {
public static void main(String[] args) {
//方式1:
// FileOutputStream fos = null;
// try {
// fos = new FileOutputStream("1.txt");
// } catch (FileNotFoundException e) {
// e.printStackTrace();
// }
// try {
// fos.write("hello world".getBytes());
// } catch (IOException e) {
// e.printStackTrace();
// }
// try {
// fos.close();
// } catch (IOException e) {
// e.printStackTrace();
// }
FileOutputStream fos = null;
try {
fos = new FileOutputStream("1.txt");
fos.write("hello world".getBytes());
} catch (FileNotFoundException e) {
e.printStackTrace();
} catch (IOException e) {
e.printStackTrace();
}finally {
if(fos != null) {
try {
fos.close();
} catch (IOException e) {
e.printStackTrace();
}
}
}
}
}
2.3.2字节输入流:
InputStream:此抽象类是表示字节输入流的所有类的超类。
2.3.2.1构造方法:
FileInputStream(String name)
2.3.2.2读入数据:
public abstract int read()
//从输入流中读取数据的下一个字节。返回 0 到 255 范围内的 int 字节值。
//下一个数据字节;如果到达流的末尾,则返回 -1。
/**
* 从系统中的文件中读入数据,显示在控制台
*/
public class FileInputStreamDemo {
public static void main(String[] args) throws IOException {
FileInputStream fis = new FileInputStream("D:\\1.txt");
int result = fis.read();
while (result !=-1){
System.out.print((char) result);
result=fis.read();
}
fis.close();
}
}
2.3.2.3复制文件:
/**
* 需求:要把一个文件的内容读取到另一个文件中,怎样操作?
*/
public class CopyFileDemo {
public static void main(String[] args) throws IOException {
FileInputStream fis = new FileInputStream("D:\\1.txt");
FileOutputStream fos = new FileOutputStream("D:\\2.txt");
int result = fis.read();
while (result != -1){
fos.write(result);
result = fis.read();
}
fos.close();
fis.close();
}
}
2.3.2.4注意事项:
①那么如果我复制的是汉字,会不会乱码呢?
答:不会,我们在读入的时候,是以字节的形式读入,输出的时候也是以字节的形式,只不过计算机帮我们隐含做了拼接操作
计算机是怎样识别的呢?
当我们的字节码出现负数的时候,将执行拼接,根据编码格式的问题,拼接个数也不同。
gbk,2个字节去拼接
utf-8,3个字节去拼接
2.3.2.5第二种读取方式:
/**
* 第二种读取方法:public int read(byte[] b) 一次读取一个字节数组
*
* 读入缓冲区的总字节数;如果因为已经到达流末尾而不再有数据可用,则返回 -1。
*/
public class FileInputStreamDemo2 {
public static void main(String[] args) throws IOException {
FileInputStream fis = new FileInputStream("D:\\1.txt");
byte [] bytes= new byte[1024];//1024字节等于1k
int len =0;
while ((len= fis.read(bytes)) !=-1){
System.out.println(new String(bytes,0,len));
}
fis.close();
}
}
2.3.2.6两种读取速度练习:
/**
* 使用一次读取一个字节数组来实现复制
*/
public class CopyDemo2 {
public static void main(String[] args) throws IOException {
FileInputStream fis = new FileInputStream("D:\\1.txt");
FileOutputStream fos = new FileOutputStream("D:\\2.txt");
byte [] bytes = new byte[1024];
int len = 0;
while ((len =fis.read(bytes)) !=-1){
fos.write(bytes);
len= fis.read(bytes);
}
fis.close();
fos.close();
}
}
注意:当读取复制的文件很大时,采用第二种一次读取一个字节数组的方法要比第一种一次读取一个字节的方法快很多。