java-IO InputStream和Reader的区别和使用

1、InputStream和Reader的区别?

InputStream是表示字节输入流的所有类的超类
Reader是用于读取字符流的抽象类
InputStream提供的是字节流的读取,而非文本读取,这是和Reader类的根本区别。
即用Reader读取出来的是char数组或者String ,使用InputStream读取出来的是byte数组。
字节流用于操作文件数据,网络传输等场景,而字符流适用于与字符串,中文有关的内容处理,因为Writer/Reader两个抽象类对字符的支持比较好。
除了这些,字符输出流写数据时是先将数据写入缓冲区,待字符输出流关闭后再写入到文件中,而字节输出流是直接写入到文件中

2、字节流 InputStream、OutputStream区别

public class ByteStream {
    public static void main(String[] args) throws Exception {
        BufferedReader1();
    }

read()功能:读取单个字符的个数,如果已经读完的话会返回-1 (其范围从 0 到 65535 )
readLine() 功能:读取一个文本行。
InputStream:是表示输入字节流所有类的超类,一般我们使用它的子类,如FileInputStream等
FileInputStream文件字节输入流 以字节形式输出文件内容

   public static void FileInputStream1() throws IOException {

        FileInputStream fi=new FileInputStream("E://file.txt");
        int i;
        //此处的FileInputStream调用的read 每次仅读取一个字节
        while((i=fi.read())!=-1)
        {
            System.out.println(i);
        }
    }

OutputStream:表示输出字输出节流所有类的超类。输出流接受输出字节并将它们发送到某个接收器。
一般我们使用它的子类,如FileOutputStream等.FileOutStream文件字节输出流 字符转换成字节保存至指定文件

 public static void FileOutStream1() throws IOException {
//        File f=new File("E://file.txt");
        OutputStream out=null;
        //也可以out=new FileOutputStream(f);
        out=new FileOutputStream("E://file.txt");
        String str="hello my sorld1";
        // 只能输出byte数组,所以将字符串变为byte数组
        byte b[]=str.getBytes();
        out.write(b);
        //文件不存在会自动创建
        out.close();

    }

InputStreamReader是从字节流到字符流的桥接器:它读取字节并使用指定的字符将它们解码为字符charset。
它使用的字符集可以通过名称指定,也可以明确指定,或者可以接受平台的默认字符集
InputStreamReader 字符输入流 封裝了InputStream在里头,它以较高级的方式,一次读取一个一个字符

  public static void InputStreamReader1() throws IOException {
        FileInputStream fi=new FileInputStream("E://file.txt");
        //指定编码集对字节进行转换,在通过char进行字符转换
        InputStreamReader isr=new InputStreamReader(fi,"utf-8");
        int i;
        while((i=isr.read()) != -1){
            System.out.println((char)i);
        }

    }

OutputStreamWriter是从字符流到字节流的桥接:写入它的字符使用指定的字节编码为字节charset。它使用的字符集可以通过名称指定,也可以明确指定,或者可以接受平台的默认字符集。
OutputStreamWriter是字符流到字节流的桥接 所以无需讲字符串或者字符转换成字节 自身提供转换

   public static void OutputStreamWriter1() throws IOException {
       File file=new File("E://file.txt");
       FileOutputStream out=new FileOutputStream(file);
       OutputStreamWriter osr=new OutputStreamWriter(out);
       String str="htoodada";
       osr.write(str);
        // osr.flush();//如果用于网络传输,记得强制刷新缓冲区,否则输出的数据只停留在缓冲区中,而无法进行网络传输
       osr.close();

    }

3、字符流 BufferedReader和BufferedWriter的区别

为了实现字节到字符的有效转换,可以从基础流中提取比满足当前读取操作所需的更多字节。为了获得最高效率 可以使用字符流
BufferedReader 字符输入流: 从字符输入流中读取文本,缓冲字符,以便有效地读取字符,数组和行。

    public static void BufferedReader1() throws IOException {
        //方案一 FileReader底层是FileInputStream,通过解码器完成字节类转换为字符流
        //FileReader等同于InputStreamReader(FileInputStream)
//        FileReader reader = new FileReader("E://file.txt");
        FileInputStream fi=new FileInputStream("E://file.txt");
        try {
        //指定编码集对字节进行转换,在通过char进行字符转换
        InputStreamReader isr=new InputStreamReader(fi,"utf-8");
        //方案一
//        BufferedReader br=new BufferedReader(reader);
            BufferedReader br=new BufferedReader(isr);
        String str;
        while((str=br.readLine()) != null){
            System.out.println(str);
        }
        } catch (Exception e) {
            // TODO Auto-generated catch block
            e.printStackTrace();
        }


    }

BufferedWriter 将文本写入字符输出流,缓冲字符,以便地写入单个字符,数字和字符串

 public static void BufferedWriter1() throws Exception {
       //方案一
//        FileOutputStream fi=null;
//        OutputStreamWriter ow=null;
//        BufferedWriter writer = null;

       //方案二   FileWriter底层还是FileOutputStream,通过解码器完成字节类转换为字符流
        //即 FileWriter 等同于 OutputStreamWriter(FileOutputStream)
        FileWriter output = null;
        BufferedWriter writer = null;
        try{

            //方案一  BufferedWriter字符输出缓冲流 封装  字符输出流
//            fi=new FileOutputStream("E://file.txt");
//            ow=new OutputStreamWriter(fi);
//            writer = new BufferedWriter(ow);

            //方案二  BufferedWriter字符输出缓冲流 封装 FileWriter

            output = new FileWriter("E://file.txt");
            writer = new BufferedWriter(output);
            writer.write("dasdasdfgsgsgsfasdf \n asdfsfds \n fdsfdsf");
        }finally{
            if(null != writer){
                writer.close();
            }
            if(null != output){
                output.close();
            }
        }
    }

}

//* PW支持两个直接对文件写操作的构造方法:
// * PrintWriter(File f)传文件名
//* PrintWriter(String s)传路径
//* PrintWriter给人一种可以直接对文件进行操作的假象
//* PW是一个高级流
//* 实际上PW包装了字节流、字符流和字符缓冲流。
// * PW负责自动行刷新
//* bw负责提高效率
//* osw负责读字符
//* fos负责写字节
//* 最后PW能够按行很快地把一个字符串变成字节写在文件中
//*/

public static void PrintWriter1()
{
    FileOutputStream os=null;
    PrintWriter pw=null;
    try {
        os =new FileOutputStream("E://file.txt");
        pw = new PrintWriter(os);
        pw.write("服务器欢迎你1");
        pw.flush();
    } catch (Exception e) {
        // TODO: handle exception
    } finally{
        //关闭资源
        try {
            if(pw!=null)
                pw.close();
            if(os!=null)
                os.close();
        } catch (IOException e) {
            e.printStackTrace();
        }
    }
}
  • 5
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
IO流: Input Output 输入输出流 自己去扩展: 1. 对象序列化和反序列化生成一个 2. 流的种类: io包下 扩展nio包下 1. IO分类: 输入流 输出流 字节流 InputStream(抽象类) OutputStream(抽象类) 字符流 Reader (抽象类) Writer(抽象类) 2.字节流:(重点) * 使用场景: * 1.字节流处理除了文本、文字相关所有的流问题,如,png/jpg/avi/map4/mp3/exe * 2.字符流只处理文本、文字相关(编码乱码问题) * * 1.输入流 abstract class InputStream:这个抽象类是表示输入字节流的所有类的超类。 * | * FileInputStream 子类:文件字节输入流 * 1. 构造方法 * FileInputStream(String name) name:表示(绝对路径、相对路径)文件名 * FileInputStream(File file) * * 2. 普通方法: //1. int read(byte[] b) 从输入流读取一些字节数,并将它们存储到缓冲区 b 。 最常用 * //2. int read() 从输入流读取数据的下一个字节。 //3. int read(byte[] b, int off, int len) 从输入流读取最多 len字节的数据到一个字节数组。 * 2.输出流 abstract class OutputStream:这个抽象类是表示输出字节流的所有类的超类。 * | * FileOutputStream 子类:文件字节输出流 * 1. 构造方法 FileOutputStream(String name) name:表示(绝对路径、相对路径)文件名 FileOutputStream(String name, boolean append) append:表示是否在该文件末尾追加数据,如果为true,表示追加,false,表示从头开始覆盖 * FileOutputStream(File file) FileOutputStream(File file, boolean append) * * 2. 普通方法: //1. void write(byte[] b, int off, int len) 将 len字节从位于偏移量 off的指定字节数组写入此文件输出流。 最常用 * //2. void write(byte[] b)将 b.length个字节从指定的字节数组写入此文件输出流。 //3. void write(int b) 将指定的字节写入此文件输出流。 3. 注意事项: 1. 必须要关闭IO流,节约资源开销 2. 关闭IO流原则,先开后关 3. IO流工具类的抽取,将所有的关流(字节流和字符流)方法抽取出来,优化代码 4. 字符流:(重点) * 使用场景:使用于处理文本相关的文件 * * Reader 抽象类: * |子类 * InputStreamReader(转换流) * |子类 * FileReader:适用于读取字符相关的文件 * 1. 构造方法: * 1.FileReader(File file) 2.FileReader(String fileName) fileName:文件名(相对路径/绝对路径) * * 2. 读取方法: * 3. int read(char[] c)读取字符到char数组中 最常用 * 2. int read()读取一个字符 * 3. int read(char[] c,int start,int length)读取制定长度的字符到char数组中 * * Writer 抽象类: * |子类 * OutputStreamWriter(转换流) * |子类 * FileWriter:适用于写出字符相关的文件 * 1. 构造方法: * 1.FileWriter(File file) 默认是false 2.FileWriter(File file, boolean append) append:表示是在文件末尾追加还是从头覆盖,如果true追加,false覆盖,默认是false 3.FileWriter(String fileName) 默认是false 4.FileWriter(String fileName, boolean append) fileName:文件名(相对路径/绝对路径) * 2. 写出方法: * 1. public Writer append(CharSequence csq,int start,int end) * 2. public Writer append(char c) * 3. public Writer append(CharSequence csq) * 4. public void write(char[] c) * 5. public void write(String str) * 6. public void write(String str,int start,int end) 5. 乱码问题:(掌握) GBK: 中文2个字节 英文、数字:1字节 UTF-8: 中文3~6个字节 英文、数字:1字节 编码:将字符串转换为字节 * 1. byte[] getBytes() 根据默认字符集将当前字符串转换为字节数组 * 2. byte[] getBytes(String charsetName) UTF-8/GBK * 按照指定的字符集将将当前字符串转换为字节数组 * * 解码:将字节转换为字符 * 1.String(byte[] bytes, int offset, int length) * 根据默认字符集将字节数组中从指定下标开始到指定长度结束的数据转换为字符串 * * 2.String(byte[] bytes, int offset, int length, String charsetName) * 根据指定字符集将字节数组中从指定下标开始到指定长度结束的数据转换为字符串 * charsetName:字符集名 例如 : "GBK"、"UTF-8" 、"ISO-8859-1" * * 不常用 * 3.String(byte[] bytes) 根据默认字符集将字节数组转换为字符串 * 4.String(byte[] bytes, String charsetName) * 根据默认字符集将字节数组转换为字符串 * * 这里会有乱码问题: * 产生的原因: * 1、因为字符集不统一,即编码和解码new String(b,0,read,"gbk")字符集不一致 * 2、因为字节流读取汉字的时候,字节数组长度不够,将一个汉字拆开了 * 解决: * 1. 用字符流用统一的字符集(最常用) * * 浏览器 : UTF-8 * 前台: * HTML :UTF-8 * CSS :UTF-8 * JS、JSP :UTF-8 * * 后台: * java :UTF-8 * * 数据库: * mysql、oracle、DB2 :UTF-8 * * 开发工具:UTF-8 * 2. 文本文件用统一的字符集 且用字符流读取和写出文本相关文件(最常用) * 3. 用一个大的字节数组(一般不用) 6. 转换流:(重点) 目前唯一一个可以设置字符集的流 (简单的理解为包装流,就是将字节流包装以下,方便操作文本相关的文件) * 使用场景: * 别人给提供了字节流,而需要处理文本文件,这时候,就需要用转换流转换一下,更方便处理文本文件 * * 作用:就是一字符流的方式读取或写出文本相关的数据 * * InputStreamReader:将字节输入流包装一下,让其更适合读取文本文件 * 构造方法: * 1.InputStreamReader(InputStream in) 创建一个使用默认字符集的InputStreamReader。 * 2.InputStreamReader(InputStream in, String charsetName) 创建一个使用指定字符集的InputStreamReader。 * 普通方法: * public int read(char[] cbuf) * int read(char[] cbuf, int offset, int length) * OutputStreamWriter:将字节输出流包装一下,让其更适合写出文本文件 * 构造方法: * 1. OutputStreamWriter(OutputStream out) 创建一个使用默认字符编码的OutputStreamWriter。 * 2. OutputStreamWriter(OutputStream out, String charsetName) 创建一个使用指定字符集的OutputStreamWriter。 普通方法: void write(char[] cbuf, int off, int len) append(CharSequence csq,int start,int end) 只有转换流可以设置字符集 7. jdk7关流的新方式: 用新结构可以自动关流 前提:该流必须是实现了一个接口 AutoCloseable 语法: try( //只能写创建流的操作,不能写其他业务操作 ){ //可能有异常的代码 }catch(异常类型1 e){ }...不需要finally关流了 8. 缓冲流:(重点)包装流 * 1.概念: 提高读取和写出效率的流 * 2.作用: 提高效率 3.使用场景:以后一律都要使用,以提高效率 建议以后都是用字节或者字符数组的方式复制文件,这样效率最高 * 4. * BufferedInputStream * 字节输入缓冲流构造方法: 1.BufferedInputStream(InputStream

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值