1、流的概念和分类
(1)流的概念
流是一个很形象的概念,当程序需要读取数据的时候,就会开启一个通向数据源的流,这个数据源可以是文件、内存或是网络连接。同理,当程序需要写入数据的时候,就会开启一个通向目的地的流。这时候你就可以想象数据就好像在这其中“流动”一样。
(2)流的分类
a、流按其流向分为“输入流”和“输出流”。
b、流按数据传输单位分为“字节流”和“字符流”。“字节流”用来读写8位二进制的字节,“字符流”用来读写16位二进制字符。
c、流按功能分为“节点流”和“过滤流”。“节点流”用于直接操作目标设备的流,例如:磁盘或一块内存区域。“过滤流”是对一个已存在的流的链接和封装,通过对数据进行处理,为程序提供功能强大、灵活的读写功能。
2、InputStream和Outputstream抽象类
字节流类用于向字节流读写8位二进制的字节。一般的,字节流类主要用于读写诸如图像或声音等的二进制数据。字节流类以InputStream和OutputStream为顶层类。他们都是抽象类。InputStream中定义的方法有:
public abstract int read();//从输入流中读取数据的下一个字节
public int read(byte[] b);//从输入流中读取一定数量的字节,并将其存储在缓冲区数组b中
public int read(byte[] b ,int off ,int len);//将输入流中最多len个数据字节读入byte数组
public long skip(long n);//跳过或者丢弃此输入流中数据的n个字节
public int available();//返回从该输入流中可以读取的字节数的估计值,而不会被下一次调用此输入流的方法阻塞
public void close();//关闭输入流并释放与该流关联的所有系统资源
OutputStream抽象类所有方法返回void值,在出错情况下抛IOException异常。需要定义OutputStream子类的应用,OutputStream必须至少提供一个写入一个字节输出的方法。OutputStream中定义的方法:
public abstract void write(int b);//将指定的字节写入此输出流。
public void write(byte[] b);//将b.length个字节从指定的byte数组写入此输出流
public void write(byte[] ,int off ,int len);//从指定的字节数组写入len个字节,从偏移off开始输出到此输出流。
public void flush();//刷新此输出流并强制任何缓冲的输出字节被写出。
public void close();//关闭输出流并释放与该流关联的所有系统资源
3、FileInputStream和FileOutputStream(它们分别是InputStream和OutputStream类的子类)
(1)每个抽象类都有多个具体的子类,这些子类对不同的外设进行处理,例如磁盘文件,网络连接,甚至是内存缓冲区。FileInputStream类表示能从文件读取字节的InputStream类。其常用的构造方法有:FileInputStream(String filepath);FileInputStream(File fileObj);FileOutputStream类表示能向文件写入字节的OutputStream类。其常用的构造方法有:FileOutputStream(String filepath);FileOutputStream(File fileObj);FileOutputStream(String filePath,boolean append);
(2)举例说明
package com.iotek.inputoutputstream;
import java.io.File;
import java.io.FileInputStream;
import java.io.FileOutputStream;
import java.io.IOException;
public class FileInputStreamOutputStreamDemo {
public static void main(String[] args) {
try {//这里不管是读取文件,还是写入文件,都应该是文件,而不是文件夹。
FileCopyUtil.copyFile(new File("G:\\bookmarks_5_8_18.html"), new File("F:\\test\\test.html"));
} catch (IOException e) {
e.printStackTrace();
}
}
}
class FileCopyUtil{
public static void copyFile(File src,File dst) throws IOException{
FileInputStream fileInputStream = new FileInputStream(src);
FileOutputStream fileOutputStream = new FileOutputStream(dst);
long time1 = System.currentTimeMillis();
/*int data = -1;
while((data = fileInputStream.read())!=-1){
fileOutputStream.write(data);
}*/
byte[] buf = new byte[1024*1024];//创建一个1M大小的缓冲区,用来存放输入流中的字节数据
int len = 0;//用来保存实际读到的字节数
while((len = fileInputStream.read(buf))!=-1){
fileOutputStream.write(buf, 0, len);//使用缓冲区对文件的进行读写操作会大大提高读写的速度
}
fileOutputStream.close();
fileInputStream.close();
long time2 = System.currentTimeMillis();
System.out.println("复制完成,一共花费:" + (time2-time1) + "毫秒");
}
}
4、ByteArrayInputStream和ByteArrayOutputStream
(1)ByteArrayInputStream是把字节数组当成源的输入流,其内部包含一个内部缓冲区,且调用close()方法关闭ByteArrayInputStream无效。它有两个构造方法,每个都需要一个字节数组提供数据源:ByteArrayInputStream(byte array[]);ByteArrayInputStream(byte array[],int start,int numBytes);ByteArrayOutputStream是把字节数组当作目标的输出流,它也有两个构造方法:ByteArrayInputStream();ByteArrayOutputStream(int numBytes);
(2)举例说明
package com.iotek.inputoutputstream;
import java.io.ByteArrayInputStream;
import java.io.ByteArrayOutputStream;
import java.io.FileOutputStream;
import java.io.IOException;
public class ByteArrayInputOutputStream {
public static void main(String[] args) throws IOException {
/*String string = "Hello,shanghai!";
ByteArrayInputStream byteArrayInputStream = new ByteArrayInputStream(string.getBytes());
int data = -1;
while((data=byteArrayInputStream.read())!=-1){
System.out.print((char)data);
}
byteArrayInputStream.close();//这里的关闭时无效的,因为没有调用操作系统底层的函数。*/
ByteArrayOutputStream byteArrayOutputStream = new ByteArrayOutputStream();
byteArrayOutputStream.write(97);
byteArrayOutputStream.write(65);
byteArrayOutputStream.write("hello,world!".getBytes());
byte[] buff = byteArrayOutputStream.toByteArray();
for(byte b:buff){
System.out.print((char)b);
}
FileOutputStream fileOutputStream = new FileOutputStream("f:\\test\\a.txt",true);//true表示可以追加
byteArrayOutputStream.writeTo(fileOutputStream);//把ByteArrayOutputStream内部缓冲区中的数据写到对应的文件输出流中
byteArrayOutputStream.close();//这里的关闭同上
}
}