-----------android培训、java培训、java学习型技术博客、期待与您交流! ------------
一、 打印流
1、概述:
(1)打印流包括:PrintStream和PrintWriter
(2)该流提供了打印方法,可将各种类型的数据都原样打印
2、字节打印流:PrintStream
构造方法中可接收的参数类型:
(1)file对象:File
(2)字符串路径:String
(3)字符输出流:OutputStream
3、字符串打印流:PrintWriter
构造方法中可接受的参数类型
(1)file对象:File
(2)字符串路径:String
(3)字节输出流:OutputStream
(4)字符输出流:Writer
4、代码示例:
import java.io.*;
class PrintDemo {
public static void main(String[] args) throws IOException {
// 键盘录入,创建读取流对象
BufferedReader bufr = new BufferedReader(new InputStreamReader(
System.in));
// 使用打印流,将文件输出
// 输出到屏幕
PrintWriter out = new PrintWriter(new FileWriter("a.txt"), true);
String line = null;
while ((line = bufr.readLine()) != null) {
if ("over".equals(line))
break;
out.println(line.toUpperCase());
// out.flush();
}
bufr.close();
out.close();
}
}
二、管道流
1、概述:
管道流主要用于连接两个线程间的通信,输入输出可以直接进行连接,通过结合线程使用。
字节流:PipedInputStream,PipedOutputStream
字符流:PipedReader,PipedWriter
2、使用步骤:
(1)要先创建一个读和写的两个类,实现Runnable接口,因为是两个不同的线程,覆盖run方法,注意,需要在内部抛异常
(2)创建两个管道流,并用connect()方法将两个流连接
(3)创建读写对象,并传入两个线程内,并start执行
3、代码示例:
import java.io.*;
class Read implements Runnable {
private PipedInputStream in;// 建立输入管道
Read(PipedInputStream in) {
this.in = in;
}
public void run()// 覆盖run方法,不能throw,只能try。
{
try {
// 读取写入的数据
System.out.println("开始写入数据,等待时间");// 测试用
Thread.sleep(3000);
byte[] buf = new byte[1024];
System.out.println("读取前。。没有数据阻塞");
int len = in.read(buf);
System.out.println("读到数据。。阻塞结束");
String s = new String(buf, 0, len);// 变成字符串
System.out.println(s);
in.close();
} catch (Exception e) {
throw new RuntimeException("管道读取流失败");
}
}
}
class Write implements Runnable {
private PipedOutputStream out;// 建立输出管道
// Write构造函数
Write(PipedOutputStream out) {
this.out = out;
}
public void run() {
try {
System.out.println("开始写入数据,等待6秒后。");// 测试用
Thread.sleep(6000);
out.write("管道流来喽~~~~".getBytes());// 字节流
out.close();
} catch (Exception e) {
throw new RuntimeException("管道输出流失败");
}
}
}
class PipedStreamDemo {
public static void main(String[] args) throws IOException {
PipedInputStream in = new PipedInputStream();
PipedOutputStream out = new PipedOutputStream();// 创建管道流
// 将读取流(输入流)和写入流(输出流)关联起来
in.connect(out);// 连接管道输入流和输出流
// 创建读写对象,并创建线程对象
Read r = new Read(in);
Write w = new Write(out);// 创建Runnable子类对象
new Thread(r).start();
new Thread(w).start();// 开启线程
}
}
/*output:
开始写入数据,等待时间
开始写入数据,等待6秒后。
读取前。。没有数据阻塞
读到数据。。阻塞结束
管道流来喽~~~~
*/
三、合并流
1、概述:
(1)SequenceInputStream可以将多个流连接成一个源
(2)构造函数:SequenceInputStream(Enumeration<? extends FileInputStream> e)
2、如何合并多个文件:
(1)创建集合,并将流对象添加进集合
(2)创建Enumeration对象,将集合元素加入。
(3)创建SequenceInputStream对象,合并流对象
(4)创建写入流对象,FileOutputStream,将数据写入流资源
(5)定义数组,将读取流数据存入数组,并将数组中元素写入文件中。
思路:
合并文件的时候,要用到集合,而Vector的效率太低,所以选择用ArrayList。
读取要用序列流SequenceInputStream。但该序列流要传入枚举类型的参数。
而枚举是Vector中的方法,ArrayList 中没有枚举方法,只有相似的Iterator迭代器。
故可建立枚举的匿名类,复写类中的方法以返回调用Iterator的方法即可。
注:匿名内部类访问的局部变量要用final修饰。
代码示例:假设有三个文件,将三者合并到一个新文件中
import java.io.*;
import java.util.*;
class SequenceDemo {
// 合并流对象
public static void sequenceFile() throws IOException {
FileOutputStream fos = null;
SequenceInputStream sis = null;
try {
// 创建集合,存储多个文件
ArrayList<FileInputStream> al = new ArrayList<FileInputStream>();
for (int i = 1; i <= 3; i++) {
al.add(new FileInputStream(i + ".txt"));
}
// 匿名内部类访问局部变量要final
final Iterator<FileInputStream> it = al.iterator();
// 创建Enumeration匿名对象
Enumeration<FileInputStream> en = new Enumeration<FileInputStream>() {
public boolean hasMoreElements() {
return it.hasNext();
}
public FileInputStream nextElement() {
return it.next();
}
};
// 合并流对象,将集合元素加入。
sis = new SequenceInputStream(en);
// 创建写入流对象,FileOutputStream
fos = new FileOutputStream("7.bmp");
byte[] b = new byte[1024 * 1024];
int len = 0;
// 循环,将数据写入流资源
while ((len = sis.read(b)) != -1) {
fos.write(b);
}
} catch (IOException e) {
throw new RuntimeException("文件操作失败");
}
// 关闭流资源
finally {
try {
if (fos != null)
fos.close();
} catch (IOException e) {
throw new RuntimeException("关闭流资源操作失败");
}
try {
if (sis != null)
sis.close();
} catch (IOException e) {
throw new RuntimeException("关闭流资源操作失败");
}
}
}
public static void main(String[] args) throws IOException {
sequenceFile();
}
}
3、切割流资源:
1、先关联文件FileInputStream
2、定义写入流变量:FileOutputStream
3、创建数组,并定义切割所需的大小|
4、循环读写数据,并每次创建一个新写入流,创建完后并写入文件中
5、关闭流资源
代码示例:
import java.io.*;
public class SplitFile {
// 切割流对象
public static void splitFile() throws IOException {
// 创建全局变量
FileInputStream fis = null;
FileOutputStream fos = null;
try {
// 创建文件读取流
fis = new FileInputStream("11.jpg");
// 创建数组
byte[] b = new byte[1024 * 1024];
int len = 0;
// 计数器
int count = 1;
// 循环写入数据
while ((len = fis.read(b)) != -1) {
// 每次创建一个新写入流,写入后关闭流资源
fos = new FileOutputStream((count++) + ".part");
fos.write(b, 0, len);
fos.close();
}
} catch (IOException e) {
throw new RuntimeException("关闭流资源操作失败");
}
// 关闭流资源
finally {
try {
if (fis != null)
fis.close();
} catch (IOException e) {
throw new RuntimeException("关闭流资源操作失败");
}
}
}
public static void main(String[] args) throws Exception {
splitFile();
}
}