理解java的I/O流:

理解java的I/O流:
Java的IO流是实现输入输出的基础,他可以方便的实现数据的输入输出操作,在Java中把不同的输入/输出园(键盘,文件,网络连接等)抽象描述为流(stream),通过流的方式允许Java程序使用相同的方式来访问不同的输入输出源。
Java把所有传统的流类型(类或抽象类)都放在java.io中包中,用以实现输入输出功能。
因为Java提供了这种IO流的抽象,所以开发者可以使用一致的IO代码去读写不同的IO流节点。

(1)流的分类:
1.输入流和输出流:
按照流的流向来分,可以分为输入流和输出流。
输入流:只能从中读取数据,而不能向其写入数据
输出流:只能向其写入数据,而不能从中读取数据。

Java的输入流主要由InputStream和Reader作为基类,而输出流主要由OutputStream和Writer作为基类,他们都是一些抽象基类,无法直接创建实例。

2.字节流和字符流:字节流和字符流的用法几乎完全一样,区别在于字节流和字符流所操作的数据单元不同,字节流操作的是8位的字节,而字符流操作的是16位的字符。

字节流主要由InputStream和OutputStream作为基类,而字符流主要由Reader和Writer作为基类。

3.节点流和处理流:
按照流的角色来分,可以分为节点流和处理流:
可以和一个特定的IO设备读写数据的流,称为节点流,节点流也被称为低级流(Low Level Stream)
处理流则用于对一个已存在的流进行连接或封装,通过封装后的流来实现数据读写的功能。处理流也被称为高级流。

当使用处理流进行输入输出时,程序并不会连接到实际的数据库,没有和实际的输入输出节点连接。使用处理流的一个明显好处是,只要使用相同的处理流,程序就可以采用完全相同的输入输出代码来翻不过问不同的数据源,随着处理流所包装节点流的变化,程序实际所有所访问的数据源也相应的发生变化。

实际上,Java使用处理流来包装节点流是一种典型的装饰器设计模式,通过使用处理流来包装不同的节点流,既可以消除不同节点流的实现差异,也可以提供更方便的方法完成输入输出功能。因此处理流也被称为包装流。

——————————————————————————————————————————
字节流和字符流:
InputStream和Reader:
InputStream和Reader是所有输入流的抽象基类,本身并不能创建实例来执行输入,但他们将成为所有输入流的模板,所以他们的方法是所有输入流都可以使用的方法:
在InputStream里包含如下三个方法:
int read() 从输入流中读取单个字节,返回所读取的字节数据(字节数据可直接转换为int类型)
int read(byte[] b) 从输入流中最多读取b.length个字节的数据,并将其存储在数组b中,返回实际读取的字节数。
int read(byte [ ] b,int off, int len): 从输出流中读取len个字节的数据,并将其存储在数据b中,并不是从数组起点开始,而是从off位置开始,返回实际读取的字节数。

在Reader里包含如下三个方法:

int read() 从输入流中读取单个字符,返回所读取的字节数据,字符数据可直接转换为int类型)
int read(char[] cbuf) 从输入流中最多读取cbuf.length个字符的数据,并将其存储在数组cbuf中,返回实际读取的字符数。
int read(char [ ] cbuf,int off, int len): 从输出流中读取len个字符的数据,并将其存储在数据cbuf中,并不是从数组起点开始,而是从off位置开始,返回实际读取的cbuf
数。

(2)InputStream和Reader都是抽象类,本身不能创建实例,但他们分别有一个用于读取文件的输入流:FileInputStrean和FileReader,他们都是节点流,会直接和指定文件关联。
//FileInputStream来读取自身
OutputStream和Writer:提供的方法
void write(int c) 将指定的字节字符流输出到输出流中,c可以代表字节和字符
void write(byte[] /char[] buf) 把字节字符数组中的数据输出到指定输出流中
void write(byte[] /char[] buf,int off,int len) 将字节数组字符数组从off位置开始,长度为len的字节字符流输出到输出流中

Writer还有如下两个方法:
void write(String str) 将str字符串里包含的字符输出到指定输出流中
void write(String str,int off ,int len)

//使用FileInputStream来执行输入,并使用FileOutputStream来执行输出,用于实现复制FileOutputStreamTest.java

import java.io.FileInputStream;
import java.io.FileNotFoundException;
import java.io.FileOutputStream;
import java.io.IOException;
public class FileOutputStreamTest{
     public static void main(String[] args) throws IOException {
           //创建数字输入流
           FileInputStream  fis=new FileInputStream("FileOutputStreamTest.java");
           //创建字节输出流
           FileOutputStream  fos=new  FileOutputStream("newFile.txt");
           byte []  bbuf=new  byte[32];
           int hasRead =0;
           //循环从输入流中取出数据
           while((hasRead=fis.read(bbuf))>0){
                //每读一次,即写入文件输出流,读了多少,就写多少
                fos.write(bbuf,0,hasRead);
           }
     }
}

处理流的用法:
(1)使用处理流的典型思路是,使用处理流来包装节点流,程序通过处理流来执行输入输出功能,让节点流与底层的IO设备文件交互。
(2)实际识别处理流非常简单,只要流的构造器参数不是一个物理节点,而是已经存在的流,那么这种流一定是处理流,而所有的节点流都是直接以物理IO作为构造器参数的。

//使用PrintStream处理流来包装OutputStream。
import java.io.FileNotFoundException;
import java.io.FileOutputStream;
import java.io.PrintStream;
public class PrintStreamTest{
     public static void main(String[] args) throws FileNotFoundException {
           FileOutputStream  fos=new FileOutputStream("test.txt");
           PrintStream  ps=new  PrintStream(fos);
           //使用PrintStream执行输出
           ps.println("普通字符串");
           //直接使用PrintStream输出对象
           ps.println(new  PrintStreamTest());
     }
}

转换流:
输入输出流体系中还提供了两个转换流,用于实现将字节流转换成字符流,其中InputStreamReader将字节输入流转换成字符输入流,OutputStreamWriter将字节输出流转换为字符输出流。

//以获取键盘输入为例来介绍转换流的做法
Java使用System.in代表标准输入,即键盘输入,但这个标准输入流是InputStream类的实例,使用不方便,而且键盘输入内容都是文本内容,所以可以使用InputStreamReader将其转换为字符输入流,普通的Reader读取内容时读取输入内容来说也不方便,可以将普通的Reader再次包装成BufferedReader,利用BufferedReader的readLine()方法可以一次读取一行内容:

import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStreamReader;
public  class  keyinTest{
     public static void main(String[] args) throws IOException {
           //将System.in对象转换为Reader对象
           InputStreamReader  reader=new  InputStreamReader(System.in);
           //将普通的Reader包装为BufferReader
           BufferedReader  br=new BufferedReader(reader);
           String  line=null;
           //采用循环方式来逐行进行读取
           while((line  =br.readLine())!=null){
                //如果程序读取的字符串是exit,则退出
                if(line.equals("exit"));
                {
                     System.exit(1);
                }
                //打印读取的内容
                System.out.println("输入内容为:"+line);
           }
     }
}



评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值