- File对象的创建方式
public File(String pathname) :通过将给定的路径名字符串转换为抽象路径名来创建新的 File实例。
public File(String parent, String child) :从父路径名字符串和子路径名字符串创建新的 File实例。
public File(File parent, String child) :从父抽象路径名和子路径名字符串创建新的 File实例。
- File类常用方法
public String getName() :获取构造方法中路径的名称(末尾部分)
String getAbsolutePath() : 获取构造方法中路径的绝对路径
public long length() :获取文件的大小,单位是字节
public boolean isDirectory() :是否为目录(文件夹)。
public boolean exists() :判断构造方法中传递的路径是否存在
public boolean createNewFile() :当且仅当具有该名称的文件尚不存在时,创建一个新的空文件。
public boolean mkdir() :创建单级文件夹
public boolean mkdirs() :即可以创建单级文件夹,又可以创建多级文件夹
public boolean delete() :删除文件和文件夹,不走回收站
- 辨别相对路径和绝对路径
绝对:以盘符开始
相对:相对当前项目的根目录而言;使用项目的跟目录可以省略书写(不是盘符开始)
绝对:D:\\Work_idea\\aa\\bb\\a.txt
相对:bb\\a.txt
- 遍历文件夹
public String[] list() :
遍历构造方法传递的文件夹,获取文件夹中每一个文件|子文件夹的名称,把多个名称存储到一个String类型的数组中返回
public File[] listFiles() :返回一个File数组,表示该File目录中的所有的子文件或目录。
遍历构造方法传递的文件夹,获取文件夹中每一个文件|子文件夹,把文件|子文件夹封装为File对象,多个File对象存储到一个File类型的数组中返回
- 递归的含义
方法自己调用自己
- 递归计算5的阶乘
public static int jc(int n) {
//方法的主体不变,每次调用自己参数在发生变化5,4,3,2,1
//递归结束的条件:获取到1的时候结束
if(n==1){
return 1;
}
//递归的目的:获取下一个被乘的数字n-1
return n * jc(n-1);
}
- 使用递归会内存溢出隐患的原因
方法自己调用自己,没有结束条件,栈内存中会有无数多个方法,如果方法过多超出了栈内存是范围就会发生内存溢出
- IO流的分类和功能
输入流:把硬盘上的数据读取到内存中
字符输入流:读取字符
字节输入流:读取字节
输出流:把内存中的数据写入到硬盘中
字符输出流:写入字符
字节输出流:写入字节
- 字节输出流写出数据到文件
1.创建FileOutputStream对象,构造方法中传递写入数据的目的地
2.调用FileOutputStream对象中的方法write,把数据写入到文件中
3.释放资源
- 字节输入流读取数据到程序
1.创建FileInputStream字节输入流对象,构造方法中绑定要读取的数据源
2.使用FileInputStream对象中的方法read,读取文件
3.释放资源
- 读取数据read(byte[])方法的原理
1.字节数组的作用?
起到缓冲作用,可以把多次读取到的字节,缓冲到数组中,一次性返回效率高
数组的长度一把定义为1024或者1024的整数倍
2.read方法的返回值int是什么?
每次读取的有效字节个数
- 字节流完成文件的复制
1.创建字节输入流对象构造方法中绑定要读取的数据源
2.创建字节输出流对象构造方法中绑定要写入的目的地
3.使用字节输入流中的方法read,读取文件
4.使用字节输出流中的方法write,把读取到字节,写入到文件中
5.释放资源
- FileWriter写数据的5个方法
void write(String str):写一个字符串数据
void write(String str,int index,int len):写一个字符串中的一部分数据, index:开始索引,len:写几个
void write(int ch):写一个字符数据,这里写int类型的好处是既可以写char类型的数据,也可以写char对应的int类型的值。'a',97
void write(char[] chs):写一个字符数组数据
void write(char[] chs,int index,int len):写一个字符数组的一部分数据, index:开始索引,len:写几个
- FileWriter中关闭和刷新方法的区别
flush方法:把内存缓冲区中的数据,刷新到文件中,流对象可以继续使用
close方法:先调用flush方法,把内存缓冲区中的数据,刷新到文件中;
然后在释放和操作系统有关的资源,并关闭流,流就不能在继续使用了
- FileWriter写数据实现换行和追加写
FileWriter追加写使用两个参数的构造方法
FileWriter(String fileName, boolean append) 根据给定的文件名以及指示是否附加写入数据的 boolean 值来构造 FileWriter 对象。
参数:
String fileName:要写入数据的文件路径
boolean append:追加写的开关,true:可以追加写;false:不能追加写(会覆盖)
FileWriter写数据时换行问题
可以使用换行符号
windows:\r\n
linux:/n
mac:/r
- FileReader读数据一次一个字符
//1.创建字符输入流FileReader对象,并且绑定要读取数据的数据源
FileReader fr = new FileReader("bb\\d.txt");
//2.使用FileReader中读取数据的read方法,读取文件中的数据
int len = 0;//记录每次读取字符
while((len = fr.read())!=-1){
System.out.print((char)len);
}
//3.释放资源
fr.close();
- FileReader读数据一次一个字符数组
//1.创建字符输入流FileReader对象,并且绑定要读取数据的数据源
FileReader fr = new FileReader("d.txt");
//2.使用FileReader中读取数据的read方法,读取文件中的数据
char[] arr = new char[1024*10];
int len = 0; //记录每次读取的有效字符个数
while((len = fr.read(arr))!=-1){
System.out.println(new String(arr,0,len));
}
//3.释放资源
fr.close();
/*
java.io.File类
文件和目录路径名的抽象表示形式。
File类封装了计算机中的文件和文件夹,我们可以使用File类中的方法操作计算机中的文件和文件夹
可以使用File中的方法创建文件|文件夹
可以使用File中的方法删除文件|文件夹
可以使用File中的方法获取文件|文件夹的路径
可以使用File中的方法遍历文件夹
可以使用File中的方法获取文件的大小
必须的记住的三个单词
file:文件
directory:目录,文件夹
path:路径
File类是一个与系统无关的类,任何的操作系统都可以使用File的功能
*/
public class Demo01File {
public static void main(String[] args) {
/*
File类的静态成员变量
static String pathSeparator 与系统有关的路径分隔符,为了方便,它被表示为一个字符串。
static char pathSeparatorChar 与系统有关的路径分隔符。
static String separator 与系统有关的默认名称分隔符,为了方便,它被表示为一个字符串。
static char separatorChar 与系统有关的默认名称分隔符。
*/
String pathSeparator = File.pathSeparator;
System.out.println(pathSeparator);//路径分隔符 windows:分号(;) linux:冒号(:)
String separator = File.separator;
System.out.println(separator);//默认名称分隔符 windows:反斜杠(\) linux:正斜杠(/)
String path = "d:\\a.txt";
path = "d:"+File.separator+"a.txt";
System.out.println(path);
}
}
/*
路径
绝对路径:以盘符开始的路径
c:\\a.txt
d:\\afadsfad\\aaa\\bbb\\bbbb
相对路径:相当于当前项目的根目录而言,我们使用项目的根目录作为路径,可以省略书写
注意:
路径是不区分大小写的
在java程序中,也可以使用一个正斜杠(/)作为文件名称分隔符
如果要使用反斜杠(\),需要写2个,本身是转义字符
*/
public class Demo02File {
public static void main(String[] args) {
show02("d:","a.txt");//d:\a.txt
show02("c:","a.txt");//c:\a.txt
show03();
}
/*
File类的构造方法:
File(File parent, String child) 根据 parent 抽象路径名和 child 路径名字符串创建一个新 File 实例。
构造方法把路径分割为了两部分
File parent:父路径
String child:子路径
好处:
父路径和子路径可以分别使用不同的路径,变化更加灵活
父路径是File类型,可以先使用File类中的方法对父路径进行一些操作,在和子路径组成一个File对象
*/
private static void show03() {
File parent = new File("d:");
File f = new File(parent,"a.txt");
System.out.println(f);//d:\a.txt
}
/*
File类的构造方法:
File(String parent, String child) 根据 parent 路径名字符串和 child 路径名字符串创建一个新 File 实例。
构造方法把路径分割为了两部分
String parent:父路径
String child:子路径
好处:
父路径和子路径可以分别使用不同的路径,变化更加灵活
*/
private static void show02(String parent, String child) {
File file = new File(parent,child);
System.out.println(file);
}
/*
File类的构造方法:
File(String pathname)通过将给定路径名字符串转换为抽象路径名来创建一个新 File 实例。
参数:
String pathname:创建路径的名称
注意:
传递的路径可以是绝对路径,也可以是相对路径
传递的路径可以是以文件结尾的,也可以是以文件夹结尾
传递的路径可以是存在的,也可以是不存在的;构造方法仅仅是把字符串的路径,转换为File对象,不考虑路径的真假
*/
private static void show01() {
File f1 = new File("c:\\a.txt");
System.out.println(f1);//c:\a.txt
File f2 = new File("c:\\abc\\aaa\\bbb");
System.out.println(f2);//c:\abc\aaa\bbb
File f3 = new File("bb");
System.out.println(f3);
}
}
import java.io.File;
/*
File类的成员方法_获取功能的方法
- public String getAbsolutePath() :返回此File的绝对路径名字符串。
- public String getPath() :将此File转换为路径名字符串。
- public String getName() :返回由此File表示的文件或目录的名称。
- public long length() :返回由此File表示的文件的长度。
*/
public class Demo03FileMethod {
public static void main(String[] args) {
show04();
}
/*
- public long length() :获取文件的大小,单位是字节
注意:
length方法只能获取文件的大小,不能获取文件夹的大小
length方法获取文件如果不存在,那么返回0
*/
private static void show04() {
File f1 = new File("D:\\base\\20201220\\cs\\测试.java");
long l1 = f1.length();
System.out.println(l1);//6195 字节
File f2 = new File("c:\\afadsfafadsf.txt");
System.out.println(f2.length());//0
File f3 = new File("D:\\base\\20201220\\cs\\avi");
System.out.println(f3.length());//0
File f4 = new File("D:\\base\\20201220");
System.out.println(f4.length());//4096
}
/*
- public String getName() :获取构造方法中路径末尾的文件|文件夹的名称
*/
private static void show03() {
File f1 = new File("c:\\abc\\aaa\\a.txt");
System.out.println(f1.getName());// a.txt
File f2 = new File("c:\\abc\\aaa");
System.out.println(f2.getName());//aaa
File f3 = new File("20201220\\abc\\b.txt");
System.out.println(f3.getName());// b.txt
}
/*
- public String getPath() 获取构造方法中传递路径
File类重写了Object类的toString方法
public String toString() {
return getPath();
}
*/
private static void show02() {
File f1 = new File("c:\\abc\\aaa\\a.txt");
System.out.println(f1.getPath());//c:\abc\aaa\a.txt
File f2 = new File("20201220");
System.out.println(f2.getPath());
System.out.println(f2.toString());
}
/*
- public String getAbsolutePath() :获取构造方法中传递的路径绝对路径
- File getAbsoluteFile() 返回此抽象路径名的绝对路径名形式。
注意:
无论构造方法中传递的路径是绝对的,还是相对的,返回的都是绝对路径
传递相对的,会在路径前边加上项目的根目录(D:\Work_idea\1220)
*/
private static void show01() {
File f1 = new File("c:\\abc\\aaa\\a.txt");
String a1 = f1.getAbsolutePath();
System.out.println(a1);//c:\abc\aaa\a.txt
File f2 = new File("1220");
System.out.println(f2.getAbsolutePath());// D:\Work_idea\1220\cd
File a2 = f2.getAbsoluteFile();
System.out.println(a2.exists());//true
}
}
import java.io.File;
/*
File类的成员方法_判断功能的方法
- public boolean exists() :此File表示的文件或目录是否实际存在。
- public boolean isDirectory() :此File表示的是否为目录。
- public boolean isFile() :此File表示的是否为文件。
*/
public class Demo04FileMethod {
public static void main(String[] args) {
show02();
}
/*
- public boolean isDirectory() 判断构造方法中传递的路径是一个以文件夹结尾的路径吗
是文件夹,返回true
不是文件夹,返回false
- public boolean isFile() 判断构造方法中传递的路径是一个以文件结尾的路径吗
是文件,返回true
不是文件,返回false
注意:
1.构造方法中的路径必须是存在的,在判断是文件还是文件夹,否则没有意义,都会返回false
2.计算机中只有文件和文件夹,所以两个方法互斥
*/
private static void show02() {
File f1 = new File("c:\\a.txt");
if(f1.exists()){
boolean b1 = f1.isDirectory();
System.out.println("b1:"+b1);//b1:false
boolean b2 = f1.isFile();
System.out.println("b2:"+b2);//b1:false
}
System.out.println("--------------------");
File f2 = new File("1220");
if(f2.exists()){
boolean b1 = f2.isDirectory();
System.out.println("b1:"+b1);//b1:true
boolean b2 = f2.isFile();
System.out.println("b2:"+b2);//b1:false
}
System.out.println("-------------------");
File f3 = new File("1220\\a.txt");
if(f3.exists()){
boolean b1 = f3.isDirectory();
System.out.println("b1:"+b1);//b1:false
boolean b2 = f3.isFile();
System.out.println("b2:"+b2);//b1:true
}
}
/*
- public boolean exists() 判断构造方法中的路径是否存在
存在:返回true
不存在:返回false
*/
private static void show01() {
File f1 = new File("c:\\a.txt");
System.out.println(f1.exists());//false
File f2 = new File("c:\\测试.txt");
System.out.println(f2.exists());//true
File f3 = new File("1220");
System.out.println(f3.exists());//true
}
}
import java.io.File;
import java.io.IOException;
/*
File类的成员方法_创建删除功能的方法
- public boolean createNewFile() :当且仅当具有该名称的文件尚不存在时,创建一个新的空文件。
- public boolean delete() :删除由此File表示的文件或目录。
- public boolean mkdir() :创建由此File表示的目录。
- public boolean mkdirs() :创建由此File表示的目录,包括任何必需但不存在的父目录。
*/
public class Demo05Method {
public static void main(String[] args) throws IOException {
show03();
}
/*
- public boolean delete() 删除构造方法中指定的文件或者文件夹
返回值:boolean
构造方法中路径存在,删除文件|文件夹,返回true
构造方法中路径不存在,文件夹中有内容,不会删除,返回false
注意:
此删除方法不走回收站,直接在硬盘删除,需要谨慎
*/
private static void show03() {
File f1 = new File("1220\\a.txt");
boolean b1 = f1.delete();
System.out.println("b1:"+b1);
File f2 = new File("1220\\a");
boolean b2 = f2.delete();
System.out.println("b2:"+b2);
File f3 = new File("1220\\aaa");
boolean b3 = f3.delete();
System.out.println("b3:"+b3);
}
/*
- public boolean mkdir() :只能创建单级文件夹
- public boolean mkdirs() :既能创建单级文件夹,又能创建多级文件夹
作用:
用于创建一个空白的文件夹
返回值:boolean
文件夹不存在,创建成功返回true
文件夹存在,不会创建,返回false;构造方法中的路径不存在,返回false
注意:
1.创建文件夹的路径需要在构造方法中给出
2.此方法只能创建文件夹,不能创建文件
*/
private static void show02() {
File f1 = new File("1220\\a");
boolean b1 = f1.mkdir();
System.out.println("b1:"+b1);
File f2 = new File("1220\\aaa\\bbb\\ccc\\ddd\\eee\\fff");
boolean b2 = f2.mkdirs();
System.out.println("b2:"+b2);
File f3 = new File("w:\\aaa");
boolean b3 = f3.mkdir();
System.out.println("b3:"+b3);//b3:false 路径不存在
}
/*
- public boolean createNewFile() :当且仅当具有该名称的文件尚不存在时,创建一个新的空文件。
作用:
用于创建一个新的空白文件
返回值:boolean
文件不存在,创建成功返回true
文件存在,不会创建,返回false(不会覆盖)
注意:
1.此方法只能创建文件,不能创建文件夹
2.创建文件的路径和名称在构造方法中给出,必须存在,否则会抛出异常
3.有些操作系统(win10),c盘是没有权限创建文件的,会抛出拒绝访问异常
*/
private static void show01() throws IOException {
File f1 = new File("d:\\aaa.txt");
boolean b1 = f1.createNewFile();
System.out.println("b1:"+b1);
File f2 = new File("1220\\c.txt");
boolean b2 = f2.createNewFile();
System.out.println("b2:"+b2);
File f3 = new File("1220\\新建文件夹");//创建一个文件,文件的名称叫新建文件夹
boolean b3 = f3.createNewFile();
System.out.println("b3:"+b3);
//File f4 = new File("w:\\a.txt");//IOException: 系统找不到指定的路径。
File f4 = new File("d:\\aaaaaaa\\a.txt");//IOException: 系统找不到指定的路径。
boolean b4 = f4.createNewFile();
}
}
import java.io.File;
/*
File类的成员方法_目录的遍历的方法
- public String[] list()
遍历文件夹,获取文件夹中每一个文件|文件夹的名称,把多个名称存储到一个String类型的数组中返回
- public File[] listFiles()
遍历文件夹,获取文件夹中每一个文件|文件夹,把文件|文件夹封装为File对象,多个File对象存储到一个File类型的数组中返回
注意:
1.遍历文件夹的路径,在构造方法中给出
2.遍历文件夹的路径必须是存在的,否则会抛出空指针异常
3.这两个方法只能遍历文件夹,不能遍历文件;如果要遍历文件,也会抛出空指针异常
*/
public class Demo06Method {
public static void main(String[] args) {
show02();
}
/*
- public File[] listFiles()
遍历文件夹,获取文件夹中每一个文件|文件夹,把文件|文件夹封装为File对象,多个File对象存储到一个File类型的数组中返回
*/
private static void show02() {
File file = new File("D:\\base\\20201220\\cs");
//File file = new File("D:\\base\\20201220\\cs\\a.txt");//NullPointerExceptiond
//File file = new File("w:\\aaa");//NullPointerExceptiond
File[] files = file.listFiles();
for (File f : files) {
System.out.println(f);
}
}
/*
- public String[] list()
遍历文件夹,获取文件夹中每一个文件|文件夹的名称,把多个名称存储到一个String类型的数组中返回
*/
private static void show01() {
File file = new File("D:\\base\\20201220\\cs");
String[] arr = file.list();
for (String s : arr) {
System.out.println(s);
}
}
}
/*
递归:方法自己调用自己
递归的分类:
1.直接递归
public void a(){
a();
}
2.间接递归
public void a(){
b();
}
public void b(){
a();
}
递归的注意事项:
1.递归必须有结束的条件,否则会抛出内存溢出的错误
2.递归有结束的条件,但是递归的次数不能太多了,否则也会抛出内存溢出的错误
3.构造方法禁止递归
什么时候使用递归:
当我们频繁的调用一个方法,方法的主体不变,每次调用的参数改变,就可以使用递归
*/
public class Demo01Recursion {
public static void main(String[] args) {
//a();
//b(1);
}
/*
3.构造方法禁止递归
构造方法是创建对象使用的,一直对象,在内存中就会有无数多个对象
*/
public Demo01Recursion() {
//Demo01Recursion();
}
/*
2.递归有结束的条件,但是递归的次数不能太多了,否则也会抛出内存溢出的错误
11420
11409
Exception in thread "main" java.lang.StackOverflowError
*/
private static void b(int i) {
//1 2 3 4 5 ....
System.out.println(i);
if(i==20000){
return;
}
b(++i);
}
/*
1.递归必须有结束的条件,否则会抛出内存溢出的错误
java.lang.StackOverflowError
*/
private static void a() {
System.out.println("a方法!");
a();
}
}
/*
练习:
使用递归计算1-n的和
*/
public class Demo02Recursion {
public static void main(String[] args) {
int s = sum(3);
System.out.println(s);
}
/*
定义一个计算1-n和的方法
1-n的和就是n-1的和
n+(n-1)+(n-2)+(n-3)+...+1
已知:
1
n:10,100,1000
未知:
n-1
递归的目的:获取下一个被加的数字n-1
递归的结束条件:当n-1=1的时候,结束获取
*/
public static int sum(int n){
//10,9,8,7,6,...1
//递归的结束条件:当n-1=1的时候,结束获取
if(n==1){
return 1;
}
//递归的目的:获取下一个被加的数字n-1
return n+sum(n-1);
}
}
/*
练习:递归求阶乘
5!=5*4*3*2*1
n! = n * (n-1) *...* 3 * 2 * 1
*/
public class Demo03Recursion {
public static void main(String[] args) {
int jc = jc(5);
System.out.println(jc);//120
}
/*
n! = n * (n-1) *...* 3 * 2 * 1
已知:
n
1
未知:
n-1
递归的结束条件:n-1=1的时候结束
递归的目的:获取n-1
*/
private static int jc(int n) {
//5,4,3,2,1
//递归的结束条件:n-1=1的时候结束
if(n==1){
return 1;
}
//递归的结束条件:n-1=1的时候结束
return n * jc(n-1);
}
}
import java.io.File;
/*
练习:使用递归遍历文件夹已经文件夹中的子文件夹
d:\\aaa
d:\\aaa\\aaa.java
d:\\aaa\\aaa.txt
d:\\aaa\\a
d:\\aaa\\a\\a.java
d:\\aaa\\a\\a.jpg
d:\\aaa\\b
d:\\aaa\\b\\B.JAVA
d:\\aaa\\b\\b.avi
*/
public class Demo04Recursion {
public static void main(String[] args) {
File file = new File("d:\\aaa");
getAllFile(file);
}
/*
定义一个方法,参数传递要遍历文件夹
方法内部对文件夹进行遍历
*/
public static void getAllFile(File dir){
System.out.println(dir);//打印遍历的文件夹
File[] files = dir.listFiles();
for (File file : files) {
//判断遍历得到的file是否是一个文件夹
if(file.isDirectory()){
//file是一个文件夹,继续遍历这个文件夹
//而我们发现getAllFile,就是一个传递文件夹,遍历文件夹的方法
//调用getAllFile方法,传递文件夹即可
getAllFile(file);// 方法自己调用自己==>递归
}else{
//file就是一个文件,打印==>toString方法
System.out.println(file);
}
}
}
}
import java.io.File;
/*
练习:文件搜索
使用递归遍历文件夹已经文件夹中的子文件夹
只打印以.java结尾的文件
d:\\aaa
d:\\aaa\\aaa.java
d:\\aaa\\aaa.txt
d:\\aaa\\a
d:\\aaa\\a\\a.java
d:\\aaa\\a\\a.jpg
d:\\aaa\\b
d:\\aaa\\b\\B.JAVA
d:\\aaa\\b\\b.avi
*/
public class Demo05Recursion {
public static void main(String[] args) {
File file = new File("d:\\aaa");
getAllFile(file);
}
/*
定义一个方法,参数传递要遍历文件夹
方法内部对文件夹进行遍历
*/
public static void getAllFile(File dir){
File[] files = dir.listFiles();
for (File file : files) {
//判断遍历得到的file是否是一个文件夹
if(file.isDirectory()){
//file是一个文件夹,继续遍历这个文件夹
//而我们发现getAllFile,就是一个传递文件夹,遍历文件夹的方法
//调用getAllFile方法,传递文件夹即可
getAllFile(file);// 方法自己调用自己==>递归
}else{
/*
需求:
只打印以.java结尾的文件
解决:
判断file是否是一个以.java结尾的文件,是则打印
实现步骤:
1.把file对象转换为String
a.file.toString() "d:\aaa\aaa.java"
b.file.getPath() "d:\aaa\aaa.java"
c.file.getName() "aaa.java"
2.使用String类中的方法endsWith判断字符串是否以.java结尾
3.是.java结尾则打印
*/
/*String s = file.getName();//获取文件末尾名称
String s1 = s.toLowerCase();//转换为小写
boolean b = s1.endsWith(".java");//判断结尾是.java吗
if(b){
System.out.println(file);
}*/
if(file.getName().toLowerCase().endsWith(".java")){
System.out.println(file);
}
}
}
}
}
一切文件数据(文本、图片、视频等)在存储时,都是以二进制数字的形式保存,都一个一个的字节,那么传输时一样如此。所以,字节流可以传输任意文件数据。在操作流的时候,我们要时刻明确,无论使用什么样的流对象,底层传输的始终为二进制数据。
import java.io.FileNotFoundException;
import java.io.FileOutputStream;
import java.io.IOException;
/*
java.io.OutputStream:字节输出流
此抽象类是表示输出字节流的所有类的超(父)类。
OutputStream里边定义了所有字节输出流中共性的成员方法,所有的子类都可以使用
共性的成员方法:
- public void close() :关闭此输出流并释放与此流相关联的任何系统资源。
- public void flush() :刷新此输出流并强制任何缓冲的输出字节被写出。
- public void write(byte[] b):将 b.length字节从指定的字节数组写入此输出流。
- public void write(byte[] b, int off, int len) :从指定的字节数组写入 len字节,从偏移量 off开始输出到此输出流。
- public abstract void write(int b) :将指定的字节输出流。
java.io.FileOutputStream:文件字节输出流 extends OutputStream
构造方法:
FileOutputStream(File file)
FileOutputStream(String name)
参数:输出的目的地
File file:输出的目的地是一个文件
String name:输出的目的地是一个文件路径
构造方法的作用:
1.会创建FileOutputStream对象
2.会根据构造方法中传递的文件|文件路径,创建一个空白的文件
3.会把FileOutputStream对象指向创建好的文件
使用字节输出流往文件中写数据的底层过程
java程序==>JVM==>操作系统(OS)==>调用系统中写数据的方法==>把数据写入到文件中
字节输出流的使用步骤(重点):
1.创建FileOutputStream对象,构造方法中绑定输出的目的地
2.使用FileOutputStream对象中的方法write,把数据写入到文件中
3.释放资源
*/
public class Demo01OutputStream {
public static void main(String[] args) throws IOException {
//1.创建FileOutputStream对象,构造方法中绑定输出的目的地
FileOutputStream fos = new FileOutputStream("1220\\a.txt");
//2.使用FileOutputStream对象中的方法write,把数据写入到文件中
//public abstract void write(int b)一次写一个字节
fos.write(97);
//3.释放资源
fos.close();
}
}
import java.io.File;
import java.io.FileNotFoundException;
import java.io.FileOutputStream;
import java.io.IOException;
import java.util.Arrays;
/*
字节输出流中写多个字节的方法
- public void write(byte[] b) 一次写字节数组中的多个字节到文件中
- public void write(byte[] b, int off, int len) 一些写字节数组的一部分到文件中,off:数组的开始索引;len:写的字节个数
ASCII:
0:48
A:65
a:97
*/
public class Demo02OutnputStream {
public static void main(String[] args) throws IOException {
//1.创建字节输出流FileOutputStream对象,构造方法绑定输出的目的地
FileOutputStream fos = new FileOutputStream(new File("1220\\b.txt"));
//2.使用FileOutputStream对象中的方法write,把数据写入到文件中
//public void write(byte[] b) 一次写字节数组中的多个字节到文件中
/*
一次写多个字节:
第一个字节是负数,那么会和第二个字节组成一个中文
第一个字节是正数,那么写出单个的字节
*/
byte[] bytes = {
65,66,67,68,69};//ABCDE
//byte[] bytes = {-65,-66,-67,68,69};//烤紻E
fos.write(bytes);
//public void write(byte[] b, int off, int len) 一些写字节数组的一部分到文件中,off:数组的开始索引;len:写的字节个数
fos.write(bytes,1,3);//BCD
//把字符串转换为字节数组,写入到文件中
byte[] bytes1 = "中国".getBytes();
System.out.println(Arrays.toString(bytes1));//[-28, -72, -83, -27, -101, -67] IDEA UTF-8编码
fos.write(bytes1);//中国
/*
在文件中显示100
*/
fos.write(49);//1
fos.write(48);//0
fos.write(48);//0
//3.释放资源
fos.close();
}
}
import java.io.FileOutputStream;
import java.io.IOException;
/*
字节输出流
1.续写(追加写):使用两个参数的构造方法
FileOutputStream(File file, boolean append)
FileOutputStream(String name, boolean append)
参数:
File file,String name:写数据的目的地
boolean append:追加写开关
true:可以追加写,使用构造方法创建对象,不会覆盖之前的文件,会往文件的结尾继续写数据
false:不可以续写,使用构造方法创建对象,文件名相同,会创建一个新的空白文件覆盖之前的文件
2.换行:使用换行符号
windows:\r\n
linux:/n
mac:/r 从 Mac OS X开始与Linux统一
*/
public class Demo03OutputStream {
public static void main(String[] args) throws IOException {
//创建FileOutputStream对象,构造方法中传递输出的目的地和追加写开关
FileOutputStream fos = new FileOutputStream("1220\\c.txt",true);
//使用FileOutputStream对象中的方法write,把数据写入到文件中
for (int i = 1; i <= 10; i++) {
fos.write(("你好"+i+"\n").getBytes());
}
//释放资源
fos.close();
}
}
import java.io.FileInputStream;
import java.io.FileNotFoundException;
import java.io.IOException;
/*
java.io.InputStream:字节输入流
此抽象类是表示字节输入流的所有类的超类。
InputStream里边定义了所有字节输入流中共性的成员方法,所有字节输入流都可以使用
共性的成员方法:
- public void close() :关闭此输入流并释放与此流相关联的任何系统资源。
- public abstract int read(): 从输入流读取数据的下一个字节。
- public int read(byte[] b): 从输入流中读取一些字节数,并将它们存储到字节数组 b中 。
java.io.FileInputStream:文件字节输入流 extends InputStream
作用:把文件中的数据,以字节的方式读取到内存中
构造方法:
FileInputStream(File file)
FileInputStream(String name)
参数:读取的数据源
File file:读取的数据源是一个文件
String name:读取的数据源是一个文件路径
构造方法的作用:
1.会创建FileInputStream对象
2.会把创建好的FileInputStream对象指向要读取的文件的第一个字节
使用字节输入流读取文件到内存中的底层原理:
java程序==>JVM==>操作系统==>调用系统中读取数据的方法==>读取文件
字节输入流的使用步骤(重点):
1.创建FileInputStream对象,构造方法中绑定要读取的数据源
2.使用FileInputStream对象中的方法read,以字节的方式读取文件
3.释放资源
*/
public class Demo01InputStream {
public static void main(String[] args) throws IOException {
//1.创建FileInputStream对象,构造方法中绑定要读取的数据源
FileInputStream fis = new FileInputStream("1220\\a.txt");//abc
//2.使用FileInputStream对象中的方法read,以字节的方式读取文件
//public abstract int read() 一次读取一个字节并返回
/*
我们发现读取文件,是一个重复的过程,所以可以使用循环优化
不知道文件中有多少数据,使用while循环
循环结束的条件,read方法读取到-1的时候结束
布尔表达式:(len = fis.read())!=-1
1.fis.read():读取一个字节
2.len = fis.read():把读取到字节赋值给len变量
3.(len = fis.read())!=-1:判断变量len的值是否不等于-1
*/
int len = 0;
while ((len = fis.read())!=-1){
System.out.print((char)len);
}
/*int len = fis.read();
System.out.println(len);//97
len = fis.read();
System.out.println(len);//98
len = fis.read();
System.out.println(len);//99
len = fis.read();
System.out.println(len);//-1*/
//3.释放资源
fis.close();
}
}
import java.io.FileInputStream;
import java.io.FileNotFoundException;
import java.io.IOException;
import java.util.Arrays;
/*
使用字节输入流一次读取多个字节
public int read(byte[] b): 从输入流中读取一些字节数,并将它们存储到字节数组 b中 。
明确两个内容
1.read方法的参数byte[]字节数组是做什么用的?
起到缓冲作用,可以把读取到的字节缓冲到数组中
一次性的由操作系统返回给JVM,由JVM返回给java程序,效率高
数组的长度一般都使用:1024或者1024的整数倍
2.read方法的返回值int是什么?
每次读取的有效字节个数
String类的构造方法:
String(byte[] bytes) 把字节数组转换为字符串
String(byte[] bytes, int offset, int length) 把字节数组一部分转换为字符串
*/
public class Demo02InputStream {
public static void main(String[] args) throws IOException {
//创建字节输入流FileInputStream对象,构造方法中绑定要读取的数据源
FileInputStream fis = new FileInputStream("1220\\b.txt");//ABCDE
//使用FileInputStream对象中的方法read,以字节的方式读取文件
//public int read(byte[] b)使用数组缓冲一次读取多个字节
/*
我们发现读取数据,是一个重复的过程,所以可以使用循环优化
不知道文件中有多少数据,使用while循环
循环结束的条件,read方法读取到-1结束
*/
byte[] bytes = new byte[1024];
int len =0;
while ((len = fis.read(bytes))!=-1){
//System.out.println(Arrays.toString(bytes));
//把字节数组的一部分转换为字符串
System.out.println(new String(bytes,0,len));
}
/*byte[] bytes = new byte[2];
int len = fis.read(bytes);
//System.out.println(Arrays.toString(bytes));
System.out.println(new String(bytes));//AB
System.out.println(len);//2
len = fis.read(bytes);
System.out.println(new String(bytes));//CD
System.out.println(len);//2
len = fis.read(bytes);
System.out.println(new String(bytes));//ED
System.out.println(len);//1
len = fis.read(bytes);
System.out.println(new String(bytes));//ED
System.out.println(len);//-1*/
//释放资源
fis.close();
}
}
import java.io.FileInputStream;
import java.io.FileOutputStream;
import java.io.IOException;
/*
文件复制案例:
原理:一读一写
数据源: c:\\1.jpg
目的地: d:\\1.jpg
实现步骤:
1.创建FileInputStream对象,绑定要读取的数据源
2.创建FileOutputStream对象,绑定要写入的目的地
3.使用FileInputStream对象中的方法read,以字节的方式读取文件
4.使用FileOutputStream对象中的方法write,把读取到字节写入到文件中
5.释放资源
*/
public class Demo01CopyFile {
public static void main(String[] args) throws IOException {
long s = System.currentTimeMillis();
//1.创建FileInputStream对象,绑定要读取的数据源
FileInputStream fis = new FileInputStream("c:\\1.exe");
//2.创建FileOutputStream对象,绑定要写入的目的地
FileOutputStream fos = new FileOutputStream("d:\\1.exe");
//3.使用FileInputStream对象中的方法read,以字节的方式读取文件
//一次读写一个字节,效率低下
/*int len = 0;
while ((len = fis.read())!=-1){
//4.使用FileOutputStream对象中的方法write,把读取到字节写入到文件中
fos.write(len);
}*/
//一次读写多个字节,效率高
byte[] bytes = new byte[1024*100];
int len = 0;
while ((len = fis.read(bytes))!=-1){
fos.write(bytes,0,len);
}
//5.释放资源
fos.close();
fis.close();
long e = System.currentTimeMillis();
System.out.println("复制文件共耗时:"+(e-s)+"毫秒!");
}
}
import java.io.FileInputStream;
import java.io.IOException;
/*
使用字节输入流读取含有中文的文件
文件的编码GBK:一个中文占用2个字节
文件的编码UTF-8:一个中文占用3个字节
*/
public class Demo01FileInputStream {
public static void main(String[] args) throws IOException {
FileInputStream fis = new FileInputStream("1220\\e.txt");
int len = 0;
while ((len = fis.read())!=-1){
System.out.print((char)len);//ÄãºÃ 使用字节流一次读取一个字节(1/2个中文),转换为字符,乱码
}
/* byte[] bytes = new byte[3];
int len = 0;
while ((len = fis.read(bytes))!=-1){
System.out.println(new String(bytes,0,len));
}*/
fis.close();
}
}
import java.io.FileNotFoundException;
import java.io.FileReader;
import java.io.IOException;
/*
java.io.Reader:字符输入流
作用:一次读取一个字符
用于读取字符流的抽象类。
是所有字符输入流的最顶层的父类,里边定义了所有字符输入流中共性的成员方法,所有字符输入流都可以使用
共性的成员方法:
- public void close() :关闭此流并释放与此流相关联的任何系统资源。
- public int read(): 从输入流读取一个字符。
- public int read(char[] cbuf): 从输入流中读取一些字符,并将它们存储到字符数组 cbuf中 。
java.io.FileReader:文件字符输入流 extends Reader
作用:把文件中的字符读取到内存中
构造方法:
FileReader(File file)
FileReader(String fileName)
参数:要读取的数据源
File file:要读取的数据源是一个文件
String fileName:要读取的数据源是一个文件路径
构造方法的作用:
1.会创建一个FileReader对象
2.会把FileReader对象指向要读取文件的第一个字符
使用字符输入流读取文件的步骤(重点):
1.创建FileReader对象,构造方法中绑定要读取的数据源
2.使用FileReader中的方法read,以字符的方式读取文件
3.释放资源
String类的构造方法
String(char[] value) 把字符数组转换为字符串
String(char[] value, int offset, int count) 把字符数组的一部分转换为字符串
参数:
int offset:数组的开始索引
int count:转换的个数
*/
public class Demo01Reader {
public static void main(String[] args) throws IOException {
//1.创建FileReader对象,构造方法中绑定要读取的数据源
FileReader fr = new FileReader("1220\\e.txt");
//2.使用FileReader中的方法read,以字符的方式读取文件
//public int read() 一次读取一个字符
/*int len = 0;
while ((len = fr.read())!=-1){
System.out.print((char)len);
}*/
//public int read(char[] cbuf)使用数组缓冲一次读取多个字符
char[] chars = new char[1024];
int len=0;
while ((len =fr.read(chars))!=-1){
System.out.println(new String(chars,0,len));
}
//3.释放资源
fr.close();
}
}
import java.io.FileWriter;
import java.io.IOException;
/*
java.io.Writer:字符输出流
是所有字符输出流最顶层的父类,里边定义了所有字符输出流中共性的成员方法,所有的字符输出流都可以使用
共性的成员方法:
- public abstract void close() :关闭此流,但要先刷新它。
- public abstract void flush() :刷新此输出流并强制任何缓冲的输出字符被写出。
- public void write(int c) :写出一个字符。
- public void write(char[] cbuf):将 b.length字符从指定的字符数组写出此输出流。
- public abstract void write(char[] b, int off, int len) :从指定的字符数组写出 len字符,从偏移量 off开始输出到此输出流。
- public void write(String str) :写出一个字符串。
- void write(String str, int off, int len) 写入字符串的某一部分。
java.io.FileWriter:文件字符输出流 extends Writer
作用:把内存中的字符,写入到文件中
构造方法:
FileWriter(File file)
FileWriter(String fileName)
参数:写入数据的目的地
File file:目的地是一个文件
String fileName:目的地是一个文件路径
构造方法的作用:
1.创建一个FileWriter对象
2.会根据构造方法中传递的文件|文件路径,创建一个新的空白的文件
3.会把FileWriter对象,指向空白的文件
字符输出流的使用步骤(重点):
1.创建FileWriter对象,构造方法中绑定要写入的目的地
2.使用FileWriter对象中的方法write,把数据写入到内存缓冲区中
3.使用FileWriter对象中的方法flush,把内存缓冲中的数据刷新到文件中
4.释放资源(会先调用flush方法,把数据刷新到文件中,在释放资源)
*/
public class Demo01Writer {
public static void main(String[] args) throws IOException {
//1.创建FileWriter对象,构造方法中绑定要写入的目的地
FileWriter fw = new FileWriter("1220\\1.txt");
//2.使用FileWriter对象中的方法write,把数据写入到内存缓冲区中
//public void write(int c) :写出一个字符。
fw.write(100);
//3.使用FileWriter对象中的方法flush,把内存缓冲中的数据刷新到文件中
//fw.flush();
//4.释放资源(会先调用flush方法,把数据刷新到文件中,在释放资源)
fw.close();
}
}
import java.io.FileWriter;
import java.io.IOException;
/*
关闭和刷新的区别
- flush :刷新缓冲区,把缓冲区中的数据刷新到文件,流对象可以继续使用。
- close :关闭流,释放系统资源。关闭前会刷新缓冲区。把缓冲区中的数据刷新到文件,关闭之后流对象就不能使用了
*/
public class Demo02Writer {
public static void main(String[] args) throws IOException {
FileWriter fw = new FileWriter("1220\\2.txt");
fw.write(65);//A
fw.write(66);//B
fw.flush();//把缓冲区中的数据刷新到文件,流对象可以继续使用
fw.write(67);//C
fw.close();//把缓冲区中的数据刷新到文件,流对象就关闭了,就不能在使用了
fw.write(68);//IOException: Stream closed
}
}
import java.io.FileWriter;
import java.io.IOException;
/*
写字符的其他方法:
- public void write(int c) :写出一个字符。
- public void write(char[] cbuf):将 b.length字符从指定的字符数组写出此输出流。
- public abstract void write(char[] b, int off, int len) :从指定的字符数组写出 len字符,从偏移量 off开始输出到此输出流。
- public void write(String str) :写出一个字符串。
- void write(String str, int off, int len) 写入字符串的某一部分。
*/
public class Demo03Writer {
public static void main(String[] args) throws IOException {
FileWriter fw = new FileWriter("1220\\3.txt");
//public void write(char[] cbuf) 写字符数组中的多个字符
char[] cs = {
'a','b','c','d','中','国'};
fw.write(cs);//abcd中国
/*
public abstract void write(char[] b, int off, int len) 写字符数组的一部分
int off:数组的开始索引
int len:写个数
*/
fw.write(cs,4,2);//中国
//public void write(String str) :写出一个字符串。
fw.write("我是一个中国人,我骄傲!");
//void write(String str, int off, int len) 写入字符串的某一部分。
fw.write("我是一个中国人,我骄傲!",0,7);
fw.close();
}
}
import java.io.FileWriter;
import java.io.IOException;
/*
字符输出流
1.续写(追加写):使用两个参数的构造方法
FileWriter(File file, boolean append)
FileWriter(String fileName, boolean append)
参数:
File file,String fileName:写数据的目的地
boolean append:追加写开关
true:可以追加写,使用构造方法创建对象,不会覆盖之前的文件,会往文件的结尾继续写数据
false:不可以续写,使用构造方法创建对象,文件名相同,会创建一个新的空白文件覆盖之前的文件
2.换行:使用换行符号
windows:\r\n
linux:/n
mac:/r 从 Mac OS X开始与Linux统一
*/
public class Demo04Writer {
public static void main(String[] args) throws IOException {
FileWriter fw = new FileWriter("1220\\4.txt",true);
for (int i = 1; i <= 10; i++) {
fw.write("hello"+i+"\r\n");
}
fw.close();
}
}
1.使用字节流读写任意的文件:任何文件都是以字节为基本单位的
使用字节流读取含有中文的文件使用,一次读取一个字节(1/2,1/3中文),使用起来不方便
2.使用字符读写文本文件:使用记事本打开能看懂的文件 一次读写一个字符