I/O系统概念:
Java内存中对一段数据序列的一次读写(输入、输出)操作,并且是以"流(stream)"的方式进行。
一、流操作基本概念:
(1)数据源:即保存数据的地方,也可以理解为数据的仓库,常见的有内存、文件、网络连接、数据库
(2)流:是指数据在数据源和程序间所经历的路径, 包括两大类:输入流和输出流
(3)输入流:数据从数据源(文件)传递到程序(内存)的路径
(4)输出流:数据从程序传递到数据源的路径
二、操作流程:
(1)打开数据源
(2)根据数据源建立相对应的输入输出流
(3)根据输入输出流进行读写操作
(4)操作完成后一定要关闭相应的输入输出流
三、Java IO流原理
(1)I/O是Input/Output,用于处理数据传输,如读/写文件,网络通讯等
(2)java.io包下提供了各种"流"类和接口,以获取不同种类的数据,并通过方法输入或者输出数据
(3)输入(Input):读取外部数据(磁盘、光盘等存储设备的数据)到程序(内存中)
(4)输出(Output):将程序(内存)数据输出到磁盘、光盘等存储设备中
四、流的分类
(1)按操作数据单位不同分为:字节流(8 bit)二进制文件、字符流(按字符)文本文件
1字符 = 2字节 、 1字节(byte) = 8位(bit) 、 一个汉字占两个字节长度
1)字节流:每次读取(写出)一个字节,当传输的资源文件有中文时,就会出现乱码
2)字符流:每次读取(写出)两个字节,有中文时,使用该流就可以正确传输显示中文
(2)按数据的流向不同分:输入流,输出流, 此输入、输出是相对于我们写的代码程序来说
1)输入流:从别的地方(本地文件,网络上的资源等)获取资源 输入到 我们的程序中
2)输出流:从我们的程序中 输出到 别的地方(本地文件), 将一个字符串保存到本地文件中,就需要使用输出流。
(3)按流的角色的不同分为:节点流,处理流/包装流
1)节点流:以从或向一个特定的地方(节点)读写数据。如FileInputStream
2)处理流:是对一个已存在的流的连接和封装,通过所封装的流的功能调用实现数据读写。如BufferedReader。处理流的构造方法总是要带一个其他的流对象做参数。一个流对象经过其他流的多次包装
1、IO流常用到的五类一接口
在整个Java.io包中最重要的就是5个类和一个接口。5个类指的是File、OutputStream、InputStream、Writer、Reader;一个接口指的是Serializable
1.2、4个基本的抽象流类型
(抽象基类) | 字节流 | 字符流 |
输入流 | InputStream | Reader |
输出流 | OutputStream | Write |
滴滴:Java的IO流共涉及40多个类,都是从如上4个抽象基类派生的,由这4个类派生出来的子类名称都是以其父类名作为子类后缀名
1.2.1、InputStream字节输入流的类层次图
1.2.2 各种字节输入流的含义
1. 2.3 字节输入流的常用方法
1.2.4 文件字节输入流FileInputStream:为了创建FileInputStream类的对象,可以使用构造方法:
1)¨public FileInputStream(String name):通过打开一个到实际文件的连接来创建一个 FileInputStream,该文件通过文件系统中的路径名 name 指定。
2)¨public FileInputStream(File file):通过打开一个到实际文件的连接来创建一个 FileInputStream,该文件通过文件系统中的 File 对象 file 指定。
滴滴:FileInputStream流顺序地读取文件,只要不关闭流,每次调用read()方法就顺序地读取文件中其余的内容,直到文件的末尾或流被关闭。
1)public void close() throws IOException
2.2.5 缓冲输入流BufferedInputStream
¨它通过重写其超类FilterInputStream的方法,在其中提供了内部缓冲操作,内部缓冲允许大量待读取的数据存入缓冲区内。即使重写了FilterInputStream的方法,其过滤机器仍保留着。使用内部缓冲,使得实际数据可以按块读取,如按照磁盘的块大小进行读取。其后的读请求由内部缓冲区来响应,这样访问速度比磁盘的访问速度快。
构造方法:
1)¨public BufferedInputStream(InputStream in);
2) public BufferedInputStream(InputStream in, int size);
第一种形式使用一个缺省的缓冲区大小,而第二种形式用构造方法的第二个参数指定缓冲区大小。
代码演示:
package io;
import java.io.BufferedInputStream;
import java.io.File;
import java.io.FileInputStream;
import java.io.IOException;
public class FileReadDemo {
public static void main(String[] args) {
File f=new File("D:\\animal\\123.txt");
FileInputStream fin=null;
/*try {
//字节流:输入流(读) 、输出流(写)
//创建一个文件输入流对象
fin=new FileInputStream(f);
int temp=0;
while((temp=fin.read())!=-1) {
System.out.print((char)(temp));
}
} catch (Exception e) {
e.printStackTrace();
}finally {
try {
fin.close();//关闭输入流
} catch (IOException e) {
e.printStackTrace();
}
}*/
/*try {
fin=new FileInputStream(f);
byte[] b=new byte[1024];
int temp=0;
while((temp=fin.read(b))!=-1) {
String str=new String(b, 0, temp);
//解决乱码,字符串转码
String s=new String(str.getBytes(), "utf-8");
System.out.println(s);
}
} catch (Exception e) {
e.printStackTrace();
}finally {
try {
fin.close();//关闭输入流
} catch (IOException e) {
e.printStackTrace();
}
}*/
BufferedInputStream bin=null;
try {
fin=new FileInputStream(f);
bin=new BufferedInputStream(fin);//缓冲输入流
byte[] b=new byte[1024];
int temp=0;
while((temp=bin.read(b))!=-1) {
String str=new String(b, 0, temp);
//解决乱码,字符串转码
String s=new String(str.getBytes(), "utf-8");
System.out.println(s);
}
} catch (Exception e) {
e.printStackTrace();
}finally {
try {
fin.close();//关闭输入流
} catch (IOException e) {
e.printStackTrace();
}
}
}
}
2.字节输出流的类层次图
2.1各种字节输出流的含义
2.2字节输出流的常用方法
2.2.1 文件类输出流FileOutputStream
构造方法格式如下:
1)public FileOutputStream(String name):创建一个向具有指定名称的文件中写入数据的输出文件流。
2)public FileOutputStream(File file):创建一个向指定 File 对象表示的文件中写入数据的文件输出流。
3)FileOutputStream(File file, boolean append):创建一个向指定 File 对象表示的文件中写入数据的文件输出流。(append - 如果为 true,则将字节写入文件末尾处,也就是追加
4)FileOutputStream(String name, boolean append) :创建一个向具有指定 name 的文件中写入数据的输出文件流。
滴滴:FileOutputStream流顺序地写文件,只要不关闭流,每次调用write( )方法就顺序地向文件写入内容,直到流被关闭。如果输出流要写入数据的文件已经存在,该文件中的数据内容就会被刷新;如果要写入数据的文件不存在,该文件就会被建立。
2.2.2 缓冲输出流BufferedOutputStream
BufferedOutputStream:继承自FilterOutputStream,该类实现缓冲的输出流。通过设置这种输出流,应用程序就可以将各个字节写入底层输出流中,而不必针对每次字节写入调用底层系统
构造方法:
1)BufferedOutputStream(OutputStream out):创建一个新的缓冲输出流,以将数据写入指定的底层输出流
2)BufferedOutputStream(OutputStream out, int size) :创建一个新的缓冲输出流,以将具有指定缓冲区大小的数据写入指定的底层输出流
常用方法:1)void flush() :刷新此缓冲的输出流。
2)void write(byte[] b, int off, int len) :将指定 byte 数组中从偏移量 off 开始的 len 个字节写入此缓冲的输出流。
3)void write(int b) :将指定的字节写入此缓冲的输出流
代码演示:
package com.io;
import java.io.BufferedOutputStream;
import java.io.File;
import java.io.FileNotFoundException;
import java.io.FileOutputStream;
import java.io.IOException;
public class FileWiterDemo {
public static void main(String[] args) throws IOException {
// 字节流:文件输出流(写)
File f=new File("D:\\a\\b\\c\\d\\1.txt");
// FileOutputStream fout=new FileOutputStream(f);//文件输出流
/*FileOutputStream fout=new FileOutputStream(f,true);//不覆盖源文件,追加新内容
String str="\r\n hello world";
fout.write(str.getBytes());//write 写入文件
fout.close();*/
FileOutputStream fout=new FileOutputStream(f,true);
BufferedOutputStream bout=new BufferedOutputStream(fout);
String str="\r\n imti";
bout.write(str.getBytes());
bout.flush();//刷新缓冲区
bout.close();//关闭输出流
}
}
例题:文件copy
package com.io;
import java.io.BufferedInputStream;
import java.io.BufferedOutputStream;
import java.io.File;
import java.io.FileInputStream;
import java.io.FileNotFoundException;
import java.io.FileOutputStream;
import java.io.IOException;
public class FileCopy {
public static void main(String[] args) throws IOException {
File f1=new File("D:\\a\\b\\c\\d\\1.txt");
File f2=new File("D:\\a",f1.getName());
FileInputStream fin=new FileInputStream(f1);//文件输入流--读
BufferedInputStream bin=new BufferedInputStream(fin);//缓冲输入流
FileOutputStream fout=new FileOutputStream(f2);//文件输出流--写
BufferedOutputStream bout=new BufferedOutputStream(fout);//缓冲输出流
byte[] b=new byte[1024];
int n=0;
while((n=bin.read(b))!=-1) {//读取文件
String str=new String(b, 0, n);
bout.write(str.getBytes());//写入文件
}
bout.flush();//刷新缓冲区
bout.close();
fout.close();
bin.close();
fin.close();
}
}
照片copy:
package io;
import java.io.BufferedInputStream;
import java.io.BufferedOutputStream;
import java.io.File;
import java.io.FileInputStream;
import java.io.FileNotFoundException;
import java.io.FileOutputStream;
import java.io.IOException;
import java.io.InputStream;
import javax.imageio.stream.FileImageOutputStream;
//将图片拷贝到另一个目录中
public class PictureCopy {
public static void main(String[] args) throws IOException {
FileInputStream f = new FileInputStream("F:\\anzhuo\\笔记\\ren.jpg");
BufferedInputStream b = new BufferedInputStream(f);
FileOutputStream fos = new FileOutputStream("F:\\QLDownload\\ren.jpg");
BufferedOutputStream bout = new BufferedOutputStream(fos);
int read;
while ((read = b.read()) != -1) {
bout.write(read);
}
bout.flush();
f.close();
b.close();
fos.close();
bout.close();
}
}
图片copy: