黑马程序员_JavaSE学习总结第20天_IO流2

------- android培训、java培训、期待与您交流! ---------- 

20.01  递归概述和注意事项

递归:方法定义中调用方法本身的现象

递归注意事项:

1.要有出口,否则就是死递归

2.次数不能太多,否则就内存溢出

3.构造方法不能递归使用

20.02  递归求阶乘的代码实现及内存图解

例:

 1 public class Practice
 2 {
 3     public static void main(String[] args)
 4     {
 5         System.out.println(jieCheng(5));
 6     }
 7     public static int jieCheng(int i)
 8     {
 9         if(i == 1)
10             return 1;
11         else
12             return i * jieCheng(i - 1);
13     }
14 }

 

20.03  不死神兔问题案例

有一对兔子,从出生后第3个月起每个月都生一对兔子,小兔子长到第三个月后每个月又生一对兔子,假如兔子都不死,问第二十个月的兔子对数为多少?

第1个月:1    第2个月:1    第3个月:2   

第4个月:3    第5个月:5    第6个月:8

...

由此可见兔子对象的数据是:1,1,2,3,5,8...

规则:A:从第三项开始,每一项是前两项之和

     B:而且说明前两项是已知的

 1 public class Practice
 2 {
 3     public static void main(String[] args)
 4     {
 5         //方式1:数组实现
 6         int[] arr = new int[20];
 7         arr[0] = 1;
 8         arr[1] = 1;
 9         for(int i = 2 ; i < arr.length; i++)
10         {
11             arr[i] = arr[i - 2] + arr[i - 1];
12         }
13         System.out.println(arr[19]);
14         System.out.println("------");
15         //方式2:变量的变化实现
16         int a = 1;
17         int b = 1;
18         for (int i = 0; i < 18; i++)
19         {
20             int temp = a;
21             a = b;
22             b = temp + b;
23         }
24         System.out.println(b);
25         System.out.println("------");
26         //方式3
27         System.out.println(sum(20));
28     }
29     //方式3:递归实现
30     public static int sum(int i)
31     {
32         if(i == 1 || i == 2)
33             return 1;
34         else
35             return sum(i - 1) + sum(i - 2);
36     }
37 }

20.04  递归输出指定目录下所有的java文件的绝对路径案例

 1 public class Practice
 2 {
 3     public static void main(String[] args)
 4     {
 5         File f = new File("E:\\javaSE");
 6         getAllJavaFilePaths(f);
 7     }
 8     public static void getAllJavaFilePaths(File srcFolder)
 9     {
10         // 获取该目录下所有的文件或者文件夹的File数组
11         File[] fileArray = srcFolder.listFiles();
12
13         // 遍历该File数组,得到每一个File对象
14         for (File file : fileArray)
15         {
16             // 判断该File对象是否是文件夹
17             if (file.isDirectory())
18             {
19                 //如果是目录继续进入
20                 getAllJavaFilePaths(file);
21             }
22             else
23             {
24                 // 继续判断是否以.java结尾
25                 if (file.getName().endsWith(".java"))
26                 {
27                     // 就输出该文件的绝对路径
28                     System.out.println(file.getAbsolutePath());
29                 }
30             }
31         }
32     }
33 }

20.05  递归删除带内容的目录案例

 1 public class Practice
 2 {
 3     public static void main(String[] args)
 4     {
 5         File f = new File("D:\\demo");
 6         deleteFolder(f);
 7     }
 8     private static void deleteFolder(File srcFolder)
 9     {
10         // 获取该目录下的所有文件或者文件夹的File数组
11         File[] fileArray = srcFolder.listFiles();
12         if (fileArray != null)
13         {
14             // 遍历该File数组,得到每一个File对象
15             for (File file : fileArray)
16             {
17                 // 判断该File对象是否是文件夹
18                 if (file.isDirectory())
19                 {
20                     deleteFolder(file);
21                 }
22                 else
23                 {
24                     file.delete();
25                     System.out.println("删除文件:"+file.getName());
26                 }
27             }
28             //删除文件夹
29             srcFolder.delete();
30             System.out.println("删除文件夹:"+srcFolder.getName());
31         }
32     }
33 }

20.06  IO流概述及分类

IO流用来处理设备之间的数据传输

Java对数据的操作是通过流的方式

Java用于操作流的对象都在IO包中

20.07  IO流基类概述

按照数据流向:输入流[读入数据]、输出流[写出数据]

按照数据类型:

字节流字节输入流[InputStream]、字节输出流[OutputStream]

字符流字符输入流[Reader]、字符输出流[Writer]

注:由这四个类派生出来的子类名称都是以其父类名作为子类名的后缀

 

InputStream:此抽象类是表示字节输入流的所有类的超类。

OutputStream:此抽象类是表示输出字节流的所有类的超类。

Reader:用于读取字符流的抽象类。

Writer:写入字符流的抽象类。

20.08  FileOutputStream的构造方法

FileOutputStream的构造方法

public FileOutputStream(File file)throws FileNotFoundException

创建一个向指定 File 对象表示的文件中写入数据的文件输出流。

public FileOutputStream(String name)throws FileNotFoundException

创建一个向具有指定名称的文件中写入数据的输出文件流。

20.09  FileOutputStream写出数据

例:

1 FileOutputStream fos = new FileOutputStream("D:\\a.txt");
2 fos.write("hello,IO".getBytes());
3 //释放资源,关闭此文件输出流并释放与此流有关的所有系统资源。
4 fos.close();

创建字节输出流对象了做了3件事情:

A:调用系统功能去创建文件

B:创建fos对象

C:把fos对象指向这个文件

字节输出流操作步骤:

A:创建字节输出流对象

B:写数据

C:释放资源

为什么一定要close()

A:让流对象变成垃圾,这样就可以被垃圾回收器回收了

B:通知系统去释放跟该文件相关的资源

20.10  FileOutputStream的三个write()方法

FileOutputStream 的方法:

1.public void write(int b)throws IOException

将指定字节写入此文件输出流。实现 OutputStream 的 write 方法。

2.public void write(byte[] b)throws IOException

将 b.length 个字节从指定 byte 数组写入此文件输出流中。

3.public void write(byte[] b,int off,int len)throws IOException

将指定 byte 数组中从偏移量 off 开始的 len 个字节写入此文件输出流。

例:

 1 public class Practice
 2 {
 3     public static void main(String[] args) throws IOException
 4     {
 5         FileOutputStream fos = new FileOutputStream("D:\\a.txt");
 6         //写一个字节
 7         fos.write(97);
 8         byte[] bys = {97,98,99,100,101};
 9         //写一个字节数组
10         fos.write(bys);
11         //写一个字节数组的一部分,从1开始写3个
12         fos.write(bys,1,3);
13         //释放资源
14         fos.close();
15     }
16 }

文件a.txt中的内容:aabcdebcd

20.11  FileOutputStream写出数据实现换行和追加写入

public FileOutputStream(String name,boolean append)throws FileNotFoundException

创建一个向具有指定 name 的文件中写入数据的输出文件流。如果第二个参数为 true,则将字节写入文件末尾处,而不是写入文件开始处。

例:

 1 public class Practice
 2 {
 3     public static void main(String[] args) throws IOException
 4     {
 5         //true表示每次将内容写到文件的末尾
 6         FileOutputStream fos = new FileOutputStream("D:\\a.txt",true);
 7         for (int i = 0; i < 10; i++)
 8         {
 9             fos.write(("hello"+i).getBytes());
10             //写入换行符,不同系统下的换行符是不一样的,Windows下为\r\n
11             fos.write("\r\n".getBytes());
12         }
13         //释放资源
14         fos.close();
15     }
16 }

20.12  FileOutputStream写出数据异常处理

 1 public class Practice
 2 {
 3     public static void main(String[] args)
 4     {
 5         FileOutputStream fos = null;
 6         try
 7         {
 8             fos = new FileOutputStream("D:\\a.txt");
 9             fos.write("hello".getBytes());
10         }
11         catch (FileNotFoundException e)
12         {
13             e.printStackTrace();
14         }
15         catch(IOException e)
16         {
17             e.printStackTrace();
18         }
19         finally
20         {
21             //fos不是null才close()
22             if(fos != null)
23             {
24                 //保证close一定会执行
25                 try {
26                     fos.close();
27                 } catch (IOException e) {
28                     e.printStackTrace();
29                 }
30             }
31         }
32     }
33 }

20.13  FileInputStream读取数据

FileInputStream的构造方法

1.public FileInputStream(File file)throws FileNotFoundException

通过打开一个到实际文件的连接来创建一个 FileInputStream,该文件通过文件系统中的 File 对象 file 指定。

2.public FileInputStream(String name)throws FileNotFoundException

通过打开一个到实际文件的连接来创建一个 FileInputStream,该文件通过文件系统中的路径名 name 指定。

 

FileInputStream的成员方法

1.public int read()throws IOException

从此输入流中读取一个数据字节。

2.public int read(byte[] b)throws IOException

从此输入流中将最多 b.length 个字节的数据读入一个 byte 数组中。

例:

 1 public class Practice
 2 {
 3     public static void main(String[] args) throws IOException
 4     {
 5         FileInputStream fis = new FileInputStream("D:\\a.txt");
 6 //        //读一个字节,没有数据返回-1
 7 //        int by = fis.read();
 8 //        System.out.println((char)by);
 9         //循环读取
10         int ch = 0;
11         while((ch = fis.read()) != -1)
12         {
13             //此处如果读中文会出现乱码,因为一个汉字占用两个字节
14             System.out.print((char)ch);
15         }
16         fis.close();
17     }
18 }

20.14  字节流复制文本文件案例(一次读一个字节)

数据源:从哪里来  a.txt--读取数据--FileInputStream 

目的地:到哪里去  b.txt--写数据--FileOutputStream

例:

 1 public class Practice
 2 {
 3     public static void main(String[] args) throws IOException
 4     {
 5         // 封装数据源
 6         FileInputStream fis = new FileInputStream("d:\\a.txt");
 7         // 封装目的地
 8         FileOutputStream fos = new FileOutputStream("d:\\b.txt");
 9
10         int by = 0;
11         while ((by = fis.read()) != -1)
12         {
13             fos.write(by);
14         }
15
16         // 释放资源
17         fos.close();
18         fis.close();
19     }
20 }

20.15  计算机是如何识别把两个字节拼接为中文

例:

1 String s = "你好中国";
2 byte[] bys = s.getBytes();
3 System.out.println(Arrays.toString(bys));

运行结果:

[-60, -29, -70, -61, -42, -48, -71, -6]

上例中在GBK编码下将"你好中国"转为字节数组发现数组中的元素都是负数

在计算机中中文的存储分两个字节:

第一个字节肯定是负数。

第二个字节常见的是负数,可能有正数。但是没影响。

20.16  字节流复制图片案例

 1 public class Practice
 2 {
 3     public static void main(String[] args) throws IOException
 4     {
 5         FileInputStream fis = new FileInputStream("C:\\06.jpg");
 6         FileOutputStream fos = new FileOutputStream("D:\\006.jpg");
 7
 8         int by = 0;
 9         while((by = fis.read()) != -1)
10         {
11             fos.write(by);
12         }
13
14         fis.close();
15         fos.close();
16     }
17 }

20.17  FileInputStream读取数据一次一个字节数组

例:

 1 public class Practice
 2 {
 3     public static void main(String[] args) throws IOException
 4     {
 5         FileInputStream fis = new FileInputStream("D:\\a.txt");
 6
 7         //数组的长度一般是1024或者1024的整数倍
 8         byte[] bys = new byte[1024];
 9         int len = 0;//定义一个变量用于接收读取的字节个数
10         while((len = fis.read(bys)) != -1)
11         {
12             //将数组的一部分转成字符串,因为数组不一定每次都是读满的
13             //读多少数据就转多少数据
14             //不需要换行符
15             System.out.print(new String(bys, 0, len));
16
17         }
18         //释放资源
19         fis.close();
20     }
21 }

20.18  字节流复制文本文件案例(一次读一个字节数组)

 1 public class Practice
 2 {
 3     public static void main(String[] args) throws IOException
 4     {
 5         //原数据
 6         FileInputStream fis = new FileInputStream("D:\\a.txt");
 7         //目的数据
 8         FileOutputStream fos = new FileOutputStream("D:\\c.txt");
 9         byte[] bys = new byte[1024];
10         int len = 0;
11         while((len = fis.read(bys)) != -1)
12         {
13             fos.write(bys, 0, len);
14         }
15         //释放资源
16         fis.close();
17         fos.close();
18     }
19 }

20.19  字节流复制视频案例

 1 public class Practice
 2 {
 3     public static void main(String[] args) throws IOException
 4     {
 5         //原数据
 6         FileInputStream fis = new FileInputStream("C:\\test.flv");
 7         //目的数据
 8         FileOutputStream fos = new FileOutputStream("D:\\aaa.flv");
 9         byte[] bys = new byte[1024];
10         int len = 0;
11         while((len = fis.read(bys)) != -1)
12         {
13             fos.write(bys, 0, len);
14         }
15         //释放资源
16         fis.close();
17         fos.close();
18     }
19 }

20.20  BufferedOutputStream写出数据

字节流一次读写一个数组的速度明显比一次读写一个字节的速度快很多,这是加入了数组这样的缓冲区效果,java本身在设计的时候,也考虑到了这样的设计思想(装饰设计模式),所以提供了字节缓冲区流

字节缓冲输出流:BufferedOutputStream

字节缓冲输入流:BufferedInputStream

 

BufferedOutputStream构造方法:

1.public BufferedOutputStream(OutputStream out)

创建一个新的缓冲输出流,以将数据写入指定的底层输出流。

2.public BufferedOutputStream(OutputStream out,int size)

创建一个新的缓冲输出流,以将具有指定缓冲区大小的数据写入指定的底层输出流。

例:

 1 public class Practice
 2 {
 3     public static void main(String[] args) throws IOException
 4     {
 5         FileOutputStream fos = new FileOutputStream("D:\\a.txt");
 6         BufferedOutputStream bos = new BufferedOutputStream(fos);
 7         //写数据
 8         bos.write("hello".getBytes());
 9         //关闭资源
10         bos.close();
11     }
12 }

20.21  BufferedInputStream读取数据

例:

 1 public class Practice
 2 {
 3     public static void main(String[] args) throws IOException
 4     {
 5         BufferedInputStream bis1 = new BufferedInputStream(new FileInputStream("D:\\a.txt"));
 6         //方式1:读一个字节
 7         int by = 0;
 8         while((by = bis1.read()) != -1)
 9         {
10             System.out.print((char)by);
11         }
12         System.out.println("------");
13         //方式2:读一个字节数组
14         BufferedInputStream bis2 = new BufferedInputStream(new FileInputStream("D:\\a.txt"));
15         byte[] bys = new byte[1024];
16         int len = 0;
17         while((len = bis2.read(bys)) != -1)
18         {
19             System.out.println(new String(bys, 0, len));
20         }
21
22         bis1.close();
23         bis2.close();
24     }
25 }

20.22  字节流四种方式复制MP4并测试效率

基本字节流一次读写一个字节        //耗时:103891毫秒

基本字节流一次读写一个字节数组   //耗时:1110毫秒

高效字节流一次读写一个字节        //耗时:1547毫秒

高效字节流一次读写一个字节数组   //耗时:953毫秒

 1 public class Practice
 2 {
 3     public static void main(String[] args) throws IOException
 4     {
 5         long time1 = System.currentTimeMillis();
 6 //        method1("C:\\test.flv","D:\\test1.flv");
 7 //        method2("C:\\test.flv","D:\\test2.flv");
 8 //        method3("C:\\test.flv","D:\\test3.flv");
 9         method4("C:\\test.flv","D:\\test4.flv");
10         long time2 = System.currentTimeMillis();
11         System.out.println("耗时:"+(time2 - time1)+"毫秒");
12     }
13     //基本字节流一次读写一个字节
14     //耗时:103891毫秒
15     public static void method1(String src,String dest) throws IOException
16     {
17         FileInputStream fis = new FileInputStream(src);
18         FileOutputStream fos = new FileOutputStream(dest);
19
20         int by = 0;
21         while((by = fis.read()) != -1)
22         {
23             fos.write(by);
24         }
25
26         fis.close();
27         fos.close();
28     }
29     //基本字节流一次读写一个字节数组
30     //耗时:1110毫秒
31     public static void method2(String src,String dest) throws IOException
32     {
33         FileInputStream fis = new FileInputStream(src);
34         FileOutputStream fos = new FileOutputStream(dest);
35
36         byte[] bys = new byte[1024];
37         int len = 0;
38         while((len = fis.read(bys)) != -1)
39         {
40             fos.write(bys,0,len);
41         }
42
43         fis.close();
44         fos.close();
45     }
46     //高效字节流一次读写一个字节
47     //耗时:1547毫秒
48     public static void method3(String src,String dest) throws IOException
49     {
50         BufferedInputStream bis = new BufferedInputStream(new FileInputStream(src));
51         BufferedOutputStream bos = new BufferedOutputStream(new FileOutputStream(dest));
52
53         int by = 0;
54         while ((by = bis.read()) != -1)
55         {
56             bos.write(by);
57         }
58
59         bos.close();
60         bis.close();
61     }
62     //高效字节流一次读写一个字节数组
63     //耗时:953毫秒
64     public static void method4(String src,String dest) throws IOException
65     {
66         BufferedInputStream bis = new BufferedInputStream(new FileInputStream(src));
67         BufferedOutputStream bos = new BufferedOutputStream(new FileOutputStream(dest));
68
69         byte[] bys = new byte[1024];
70         int len = 0;
71         while ((len = bis.read(bys)) != -1)
72         {
73             bos.write(bys, 0, len);
74         }
75
76         bos.close();
77         bis.close();
78     }
79 }
时间: 2024-10-14 11:24:46

黑马程序员_JavaSE学习总结第20天_IO流2的相关文章

黑马程序员_JavaSE学习总结第19天_IO流1

------- android培训.java培训.期待与您交流! ----------  19.01  集合的特点和数据结构总结 HashSet.HashMap.Hashtable判断元素唯一性的方式: 通过对象的hashCode和equals方法来完成元素唯一性 如果对象的hashCode值不同,那么不用判断equals方法,就直接存储到哈希表中. 如果对象的hashCode值相同,那么要再次判断对象的equals方法是否为true. 如果为true,视为相同元素,不存.如果为false,那么

黑马程序员_JavaSE学习总结第22天_IO流4

------- android培训.java培训.期待与您交流! ----------  22.01  数据输入输出流的概述和讲解 操作基本数据类型 public class DataInputStreamextends FilterInputStream implements DataInput 数据输入流允许应用程序以与机器无关方式从底层输入流中读取基本 Java 数据类型.应用程序可以使用数据输出流写入稍后由数据输入流读取的数据. public class DataOutputStream

黑马程序员_JavaSE学习总结第21天_IO流3

------- android培训.java培训.期待与您交流! ----------  21.01  转换流出现的原因及格式 由于字节流操作中文不是特别方便,所以,java就提供了转换流. 字符流 = 字节流 + 编码表 21.02  编码表概述和常见编码表 编码表:计算机只能识别二进制数据,早期又来是电信号,为了方便应用计算机,让它可以识别各个国家的文字,就将各个国家的文字用数字来表示,并一一对应,形成一张表,就是编码表. 简单的说编码表就是由字符及其对应的数值组成的一张表.   常见的编码

黑马程序员_JavaSE学习总结第10天_面向对象5

------- android培训.java培训.期待与您交流! ----------  10.01 运动员和教练案例分析 教练和运动员案例:运动员分乒乓球运动员和篮球运动员,教练分乒乓球教练和篮球教练.为了出国交流,跟乒乓球相关的人员都需要学习英语. 分析:   10.02 运动员和教练案例实现 1 //定义一个说英语的接口 2 interface SpeakEnglish 3 { 4 //说英语 5 public abstract void speak(); 6 } 7 8 //定义人的抽象

黑马程序员_JavaSE学习总结第11天_开发工具 &amp; API常用对象1

------- android培训.java培训.期待与您交流! ----------  11.01 常见开发工具介绍 1:操作系统自带的记事本软件 2:高级记事本软件例:Editplus,Notepad++,UltraEdit 3:集成开发环境 IDE(Integrated Development Environment) 这种软件是用于程序开发环境的应用程序,一般包括代码编辑器,编译器,调试器和图形界面工具. 集成了代码编写功能,分析功能,编译功能,调试功能等一体化的开发软件.具备这一特性的

黑马程序员_JavaSE学习总结第08天_面向对象3

------- android培训.java培训.期待与您交流! ----------  08.01 工具类中使用静态 例: 1 class ArrayTool 2 { 3 //将构造方法私有,外界不能创建该类的对象 4 private ArrayTool(){} 5 //遍历数组 6 public static void print(int[] arr) 7 { 8 System.out.print("["); 9 for(int i = 0;i < arr.length;i+

黑马程序员_JavaSE学习总结第13天_API常用对象3

------- android培训.java培训.期待与您交流! ----------  13.01 StringBuffer的概述 StringBuffer类概述:线程安全的可变字符序列.一个类似于 String 的字符串缓冲区,但不能修改.虽然在任意时间点上它都包含某种特定的字符序列,但通过某些方法调用可以改变该序列的长度和内容. StringBuffer和String的区别:StringBuffer长度和内容可变,String不可变.使用StringBuffer做字符串的拼接不会浪费太多资

黑马程序员_JavaSE学习总结第16天_集合框架2

------- android培训.java培训.期待与您交流! ----------  16.01 ArrayList存储字符串并遍历 ArrayList类概述:底层数据结构是数组,查询快,增删慢,线程不安全,效率高 ArrayList类是List 接口的大小可变数组的实现.实现了所有可选列表操作,并允许包括 null在内的所有元素.除了实现 List 接口外,此类还提供一些方法来操作内部用来存储列表的数组的大小. 例: 1 public class Practice 2 { 3 public

黑马程序员_JavaSE学习总结第12天_API常用对象2

------- android培训.java培训.期待与您交流! ----------  12.01 Scanner的概述和构造方法原理 Scanner类概述:JDK5以后用于获取用户的键盘输入 构造方法:public Scanner(InputStream source) public static final InputStream in:“标准”输入流. 此流已打开并准备提供输入数据.通常,此流对应于键盘输入或者由主机环境或用户指定的另一个输入源. 12.02 Scanner类的hasNe