您的位置:首页 > 职场人生

黑马程序员——IO流——递归,字节流,字符流

2015-08-28 20:55 525 查看
------Java培训、Android培训、iOS培训、.Net培训、期待与您交流!
-------

一.递归

(1)方法定义中调用方法本身的现象

(2)递归的注意事项;

A:要有出口,否则就是死递归

B:次数不能过多,否则内存溢出

C:构造方法不能递归使用

(3)递归案例:


A:递归求阶乘

<span style="font-family:FangSong_GB2312;font-size:18px;"><strong>package cn.bolg;

public class Demo {

/**
* 递归求5的阶乘
* 分析:就是求1*2*3*4*5
* 可以看做	5*4的阶乘,4的阶乘就是4*3的阶乘依次类推
* 我们就可以定义求阶乘的方法了
*/
public static void main(String[] args) {
//调用方法
int num = method(5);
System.out.println(num);

}

public static int method(int n){
//确定阶乘出口如果n==1,就返回1
if(n==1){
return 1;
}
//返回n的阶乘的值
return n*method(n-1);

}

}</strong></span>


B:求斐波那契数列第15项的值.斐波那契数列前10项为 1,1,2,3,5,8,13,21,34,55

<span style="font-family:FangSong_GB2312;font-size:18px;"><strong>package cn.bolg;

/*
* 求斐波那契数列第15项的值.斐波那契数列前10项为 1,1,2,3,5,8,13,21,34,55
*
* 分析:1.根据斐波那契数列前10项的值可以得出规律
* 		从第3项开始:  	当前项的值	=  当前项的前一项的值  +  当前项的前一项的前一项值
*
* 	   2.我们使用递归方式求斐波那契数列第n项的值
* 		使用递归我们必须要定义递归方法的出口:
* 								当是第1项和第2项时,返回1
*
*/
public class Demo2 {

public static void main(String[] args) {
// 调用方法获得第15项对应的值
int value = method(15);
// 输出结果
System.out.println("第15项的值为:" + value);
}

// 使用递归方式定义方法,方法中参数为当前的项数
public static int method(int n) {
// 递归出口(当是第1项和第2项时,返回1)
if (n == 1 || n == 2) {
return 1;
}
// 递归调用(当前项的值=当前项的前一项的值 +当前项的前一项的前一项值)
return method(n - 1) + method(n - 2);
}

}
</strong></span>


C:递归删除带内容的目录



<span style="font-family:FangSong_GB2312;font-size:18px;"><strong>package cn.bolg;

import java.io.File;

public class Demo3 {

/**
* 递归删除带内容的目录
*/
public static void main(String[] args) {
//创建文件对象
File file = new File("F:\\a");
//调用方法删除目录
delete(file);
}

public static void delete(File file){
//判断文件有无内容
if (file.isDirectory()) {
//将文件对象转成数组
File[] listFiles = file.listFiles();
//遍历文件数组
for (File file2 : listFiles) {
//使用递归操作文件对象
delete(file2);
}
}else{
//如果是文件,直接删除
file.delete();
}
//空文件夹直接删除
file.delete();
}

}
</strong></span>


二.IO流

1.IO流概述

(1)IO用于在设备间进行数据传输的操作

(2)分类:

A:流向

输入流 读取数据

输出流 写出数据

B:数据类型

字节流

字节输入流

字节输出流

字符流

字符输入流

字符输出流

2.字节流

(1)FileOutputStream写出数据

A:使用步骤

a:创建字节输出流对象

b:调用write()方法进行写出数据

c:关闭字节输出流对象释放资源

(2)FileInputStream读取数据

A:使用步骤

a:创建字节输入流对象

b:调用read()方法进行读取数据

c:关闭字节输入流对象释放资源

(3)字节缓冲区流(高效字节流)

使用步骤与普通流一样,只需要在创建字节缓冲区流对象时将普通流传入即可.

A:BufferedOutputStream

B:BufferedInputStream

(4)字节流使用综合案例:

使用字节流四种复制方式分别复制文件

<span style="font-family:FangSong_GB2312;font-size:18px;"><strong>package cn.bolg;

import java.io.BufferedInputStream;
import java.io.BufferedOutputStream;
import java.io.FileInputStream;
import java.io.FileOutputStream;
import java.io.IOException;

public class Demo4 {

/**
* 使用字节流四种复制方式分别复制文件
* @throws IOException
*/
public static void main(String[] args) throws IOException {
//调用方法进行复制
method1();
method2();
method3();
method4();
}

// 方法一:使用普通字节流一次一个字节复制文件
public static void method1() throws IOException {
// 创建流对象
FileInputStream fis = new FileInputStream("a.txt");
FileOutputStream fos = new FileOutputStream("b.txt");
// 读取数据
int b;
while ((b = fis.read()) != -1) {
// 写出数据
fos.write(b);
}
// 关闭流
fos.close();
fis.close();

}

// 方法二:使用普通字节流一次一个字节数组复制文件
public static void method2() throws IOException {
// 创建流对象
FileInputStream fis = new FileInputStream("a.txt");
FileOutputStream fos = new FileOutputStream("b.txt");
// 读取数据
int len;
byte[] bytes = new byte[1024];
while ((len = fis.read(bytes)) != -1) {
// 写出数据
fos.write(bytes, 0, len);
}
// 关闭流
fos.close();
fis.close();
}

// 方法三:使用缓冲区字节流一次一个字节复制文件
public static void method3() throws IOException {
// 创建流对象
BufferedInputStream bis = new BufferedInputStream(new FileInputStream("a.txt"));
BufferedOutputStream bos = new BufferedOutputStream(new FileOutputStream("b.txt"));
// 读取数据
int b;
while ((b = bis.read()) != -1) {
// 写出数据
bos.write(b);
}
// 关闭流
bos.close();
bis.close();
}

// 方法四:使用缓冲区字节流一次一个字节数组复制文件
public static void method4() throws IOException {
// 创建流对象
BufferedInputStream bis = new BufferedInputStream(new FileInputStream("a.txt"));
BufferedOutputStream bos = new BufferedOutputStream(new FileOutputStream("b.txt"));
// 读取数据
int len;
byte[] bytes = new byte[1024];
while ((len = bis.read(bytes)) != -1) {
// 写出数据
bos.write(bytes, 0, len);
}
// 关闭流
bos.close();
bis.close();
}

}
</strong></span>


3.字符流

(1)主要针对文本文件这样的数据操作

Reader

a.InputStreamReader:子类FileReader

b.BufferedReader

Writer

a.OutputStreamWriter:子类FileWriter

b.BufferedWriter

(2)FileWriter写入数据

使用步骤:

A:创建字符输出流对象

B:调用对象的write()方法写入数据

C:字符输出流释放资源

(3)FileReader读取数据

使用步骤:

A:创建字符输入流对象

B:调用对象的read()方法读取数据

C:字符输入流释放资源

(4)字符缓冲区流(高效字符流)

使用步骤与普通流一样,只需要在创建字符缓冲区流对象时将普通流传入即可.

A:BufferedWriter

B:BufferedReader

(5)字符流使用综合案例:

使用字符流五种复制方式分别复制文本文件

<span style="font-family:FangSong_GB2312;font-size:18px;"><strong>package cn.bolg;

import java.io.BufferedReader;
import java.io.BufferedWriter;
import java.io.FileReader;
import java.io.FileWriter;
import java.io.IOException;

public class Demo5 {

/**
* 使用字符流五种复制方式分别复制文本文件
* @throws IOException
*/
public static void main(String[] args) throws IOException {
//调用方法对文本文件进行复制
method1();
method2();
method3();
method4();
method5();
}

// 方法一:使用普通字符流一次一个字符复制文件
public static void method1() throws IOException {
// 创建流对象
FileReader fr = new FileReader("a.txt");
FileWriter fw = new FileWriter("b.txt");
// 读取数据
int c;
while ((c = fr.read()) != -1) {
// 写出数据
fw.write(c);
}
// 关闭流
fw.close();
fr.close();

}

// 方法二:使用普通字符流一次一个字符数组复制文件
public static void method2() throws IOException {
// 创建流对象
FileReader fr = new FileReader("a.txt");
FileWriter fw = new FileWriter("b.txt");
// 读取数据
int len;
char[] chars = new char[1024];
while ((len = fr.read(chars)) != -1) {
// 写出数据
fw.write(chars, 0, len);
}
// 关闭流
fw.close();
fr.close();
}

// 方法三:使用缓冲区字符流一次一个字符复制文件
public static void method3() throws IOException {
// 创建流对象
BufferedReader br = new BufferedReader(new FileReader("a.txt"));
BufferedWriter bw = new BufferedWriter(new FileWriter("b.txt"));
// 读取数据
int c;
while ((c = br.read()) != -1) {
// 写出数据
bw.write(c);
}
// 关闭流
bw.close();
br.close();
}

// 方法四:使用缓冲区字符流一次一个字符数组复制文件
public static void method4() throws IOException {
// 创建流对象
BufferedReader br = new BufferedReader(new FileReader("a.txt"));
BufferedWriter bw = new BufferedWriter(new FileWriter("b.txt"));
// 读取数据
int len;
char[] chars = new char[1024];
while ((len = br.read(chars)) != -1) {
// 写出数据
bw.write(chars, 0, len);
}
// 关闭流
bw.close();
br.close();
}

// 方法五:使用缓冲区字符流一次一行复制文件
public static void method5() throws IOException {
// 创建流对象
BufferedReader br = new BufferedReader(new FileReader("a.txt"));
BufferedWriter bw = new BufferedWriter(new FileWriter("b.txt"));
// 读取数据
String line;
while ((line = br.readLine()) != null) {
// 写出数据
bw.write(line);
//换行
bw.newLine();
}
// 关闭流
bw.close();
br.close();
}

}
</strong></span>


4.IO流小结

A:字节流

a:字节输入流

InputStream

int read():一次读取一个字节

int read(byte[] bys):一次读取一个字节数组

子类:FileInputStream

子类:BufferedInputStream

b:字节输出流

OutputStream

void write(int by):一次写一个字节

void write(byte[] bys,int index,int len):一次写一个字节数组的

子类:FileOutputStream

子类:BufferedOutputStream

B:字符流

a:字符输入流

Reader

int read():一次读取一个字符

int read(char[] chs):一次读取一个字符数组

子类:InputStreamReader

|--FileReader

子类:BufferedReader

String readLine():一次读取一个字符串

b:字符输出流

Writer

void write(int ch):一次写一个字符

void write(char[] chs,int index,int len):一次写一个字符数组

子类:OutputStreamWriter

|--FileWriter

子类:BufferedWriter

void newLine():换行操作

void write(String line):一次写一个字符串(一行)

5.案例


A:把集合中的数据存储到文本文件

<span style="font-family:FangSong_GB2312;font-size:18px;"><strong>package cn.bolg;

import java.io.BufferedWriter;
import java.io.FileWriter;
import java.io.IOException;
import java.util.ArrayList;

public class Test {

/**
* 把集合中的数据存储到文本文件
* @throws IOException
*/
public static void main(String[] args) throws IOException {
//创建字符输出流
BufferedWriter bw = new BufferedWriter(new FileWriter("a.txt"));
//创建集合对象
ArrayList<String> al = new ArrayList<String>();
//向集合中添加元素
al.add("奔跑吧兄弟");
al.add("欢乐喜剧人");
al.add("极限挑战");
al.add("极速前进");

//遍历集合
for (String string : al) {
//写入文件中
bw.write(string);
//换行
bw.newLine();
}

//关闭流
bw.close();
}

}
</strong></span>


B:把文本文件中的数据读取到集合并遍历集合

<span style="font-family:FangSong_GB2312;font-size:18px;"><strong>package cn.bolg;

import java.io.BufferedReader;
import java.io.FileReader;
import java.io.IOException;
import java.util.ArrayList;

public class Test2 {

/**
* 把文本文件中的数据读取到集合并遍历集合
* @throws IOException
*/
public static void main(String[] args) throws IOException {

//创建字符输出流
BufferedReader br = new BufferedReader(new FileReader("a.txt"));
//创建集合
ArrayList<String> al = new ArrayList<String>();

//读取数据
String line;
while ((line= br.readLine())!=null) {
al.add(line);
}

//遍历集合
for (String string : al) {
System.out.println(string);
}

//关闭流
br.close();
}

}
</strong></span>


C:复制单级文件夹

<span style="font-family:FangSong_GB2312;font-size:18px;"><strong>package cn.bolg;

import java.io.File;
import java.io.FileInputStream;
import java.io.FileOutputStream;
import java.io.IOException;

public class Test3 {

/**
* 复制单级文件夹
* @throws IOException
*/
public static void main(String[] args) throws IOException {

//创建两个文件夹对象
File srcDir= new File("a");
File destDir = new File("b");
//调用方法复制单级文件
copyFile(srcDir,destDir);
}

public static void copyFile(File srcDir,File destDir) throws IOException{
//首先判断目标文件夹是否存在
if(!destDir.exists()){
destDir.mkdirs();
}
//将源文件对象转化为文件对象数组
File[] listFiles = srcDir.listFiles();
//遍历文件对象数组,进行复制
for (File file : listFiles) {
//获取源文件和目标文件
File srcFile = file;
File destFile = new File(destDir, srcFile.getName());

//创建流对象
FileInputStream fis = new FileInputStream(srcFile);
FileOutputStream fos = new FileOutputStream(destFile);

//读取文件数据
int b;
while ((b=fis.read())!=-1) {
//写入文件数据
fos.write(b);
}
//关闭流
fos.close();
fis.close();
}

}

}
</strong></span>


D:复制多级文件夹

<span style="font-family:FangSong_GB2312;font-size:18px;"><strong>package cn.bolg;

import java.io.BufferedReader;
import java.io.BufferedWriter;
import java.io.File;
import java.io.FileReader;
import java.io.FileWriter;
import java.io.IOException;

public class Test4 {

/**
* 复制多级文件夹
* @throws IOException
*/
public static void main(String[] args) throws IOException {
//创建文件对象
File srcDirs = new File("a");
File destDirs = new File("c");

//调用方法复制多级文件夹
copyDirs(srcDirs,destDirs);
}
//定义复制文件夹方法copyDirs
public static void copyDirs(File srcDirs,File destDirs) throws IOException{

if (srcDirs.isDirectory()) {
//首先创建目标文件
File newForld = new File(destDirs,srcDirs.getName());
newForld.mkdirs();
//将源文件文件对象转成文件对象数组
File[] files = srcDirs.listFiles();
//遍历files
for (File file : files) {

copyDirs(file,newForld);
}
}else{
File srcFile = srcDirs;
File destFile = new File(destDirs,srcFile.getName());
copyFile(srcFile,destFile);
}

}

//定义复制文件方法copyFile
public static void copyFile(File srcFile,File destFile) throws IOException{
//创建流对象
BufferedReader  br = new BufferedReader(new FileReader(srcFile));
BufferedWriter bw = new BufferedWriter(new FileWriter(destFile));
//复制文件
//读取数据
int len;
char[] chars = new char[1024];
while ((len= br.read(chars))!=-1) {
//写入数据
bw.write(chars, 0, len);
}

//关闭流
bw.close();
br.close();

}

}
</strong></span>


E:用Reader模拟BufferedReader的特有功能

<span style="font-family:FangSong_GB2312;font-size:18px;"><strong>package cn.bolg;

import java.io.IOException;
import java.io.Reader;

/**
* 用Reader模拟BufferedReader的特有功能
*/
public class Test5 {
//将Reader作为成员变量进行使用
private Reader reader;
//有参构造方法
public Test5(Reader reader) {
super();
this.reader = reader;
}
//定义一次读取一行的方法
public String myReadLine() throws IOException{
//使用字符串缓冲区接收读到的数据
StringBuilder sb = new StringBuilder();
//使用一次读取一个字符的方式
int c;
while ((c=reader.read())!=-1) {
//当字符读出来的是\r时,使用continue语句跳出不做添加
if (c=='\r') {
continue;
}
//当读到\n时,一行读取完毕,返回字符串缓冲区
if(c=='\n'){
return sb.toString();
}
//将读取到的内容存到缓冲区中
sb.append(c);
}
//如果最后一行数据没有\r\n,但是有内容,使用缓冲区长度进行判断,不等于0就返回
if (sb.length()!=0) {
return sb.toString();
}
//最后没有内容就返回null
return null;

}
//定义关闭流的方法
public void close() throws IOException{
reader.close();
}

}
</strong></span>
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: