Java IO:字节流、字符流、缓冲流分析及案例说明
创始人
2025-05-28 16:37:48
0次

1.前言

  java IO类库我一直觉得是一个比较难理解的类库,从我在小白时期学习的时候就觉得比较难。最近又重新学习思考了下,把自己的一些分析和思考分享一下。

2.IO是什么?

  IO在计算机中指Input、Output,即输入和输出,是计算机中应用程序与各种外部设备之间的数据传递,比如磁盘(文件)、网络(网络连接)、键盘等这些设备,其中这里Input和Output的是以计算机的角度来看待的。

3.Java的IO类库

3.1 Java IO类库的基础框架

在这里插入图片描述
  从这个图上门看到,Java IO非常庞大,但是层次上还是比较清晰的,所有的其实都是围绕着两个大的主干(字节流和字符流)来扩展的。
  所谓字节(Byte),是一种存储的计量单位,表示数据量多少,是计算机存储容量的计量单位,一个字节占8位;而字符(Character)是计算机使用的文字和符号,比如’a’,‘中’,'#'等;在ASCII码中,一个英文字母占用一个字节,一个汉字占用两个字节;在UTF-8编码中,一个英文字母占用一个字节,一个汉字占用三个字节,在Unicode编码中,一个英文字符占用一个字节,一个汉字占用两个字节。
  Java中通过流(stream)来处理IO,那什么是流(stream)呢?其实流是一种抽象的概念,通过先进先出的方式,把一连串的数据(字节/字符)发送出去的通道。
在这里插入图片描述
  如上图所示,当程序需要读取数据时,就开启一个从数据源到计算机程序(内存)的管道,将数据传输过去;当程序需要往目标文件写出数据时,就会开启一个从计算机程序(内存)到目标文件的管道,把数据传输过去,写入文件。这些数据就像是水流一样,在管道中按照顺序流动。
  从上面的描述我们可以看到,流基本上有以下几个特点:

  1. 顺序性-先进先出:最先读入输入流的数据最先被计算机程序接收;最先写入到输出流的数据最新被目标文件接收;
  2. 只读或只写:每个流只能是输入流或者输出流,即一个管道要么是输出,要么是输入,不能二者兼得。

3.2 Java IO的分类

  1. 按照数据流向:输入流和输出流
  2. 按照数据单位:字节流和字符流
    在这里插入图片描述
      对于输入流和输出流比较好理解,但为什么有了字节流,还要出现字符流?以UTF-8编码为例,一个英文字母对应一个字节,那么一次读取一个字节是没有问题的,但遇到中文,一个汉字对应三个字节,如果每次读取一个字节,就会把整个汉字给割裂开来,就会出现乱码,所以为了更方便的处理中文、日文、韩文等这些字符,就推出了字符流。
      我们可以看几个例子如下:
 public static void main(String[] args) throws IOException, InterruptedException {char a = (char)System.in.read();System.out.println(a);}

我们输入a,会返回 a:
在这里插入图片描述
如果我们输入“中”,会返回乱码:
在这里插入图片描述
这是因为System.in.read()一次只能读取一个字节,其范围是-1~255,(其中-1表示到了结尾),但“中”占用了三个字节,所以会出现乱码。
  字节流和字符流的主要区别:
在这里插入图片描述

3.3 Java IO的基本用法

3.3.1 字节流

3.3.3.1 用字节流写文件

    public static void main(String[] args) throws IOException {String s ="你好";byte[] bytes = s.getBytes("utf-8");File file = new File("D:/data.txt");OutputStream os = new FileOutputStream(file);os.write(bytes);os.close();}

3.3.3.2 用字节流读文件

    public static void main(String[] args) throws IOException {File file = new File("d:/data.txt");InputStream is = new FileInputStream(file);byte[] bytes = new byte[(int) file.length()];is.read(bytes);System.out.println(new String(bytes));is.close();}

3.3.3.3 用字节流copy文件

    public static void copyFile(String srcPath, String destPath) throws IOException {File src = new File(srcPath);File dest = new File(destPath);if (!src.isFile()) {throw new RuntimeException("拷贝的源文件不是文件类型,请检查源文件");}InputStream is = new FileInputStream(src);OutputStream os = new FileOutputStream(dest);//设置一个缓存区,每次读取一个字节,从输入流中一个字节一个字节的,将读取的字节放入这下面这个字节数组中,//如果字节数组满了,然后将此字节数组写入到输出流中byte[] bufferBytes = new byte[1024];int length = 0;//如果是-1,说明已经到文件结尾了,就暂停了;//如果不是-1,当bufferBytes字节数组满了以后,就将此字节数组写入到输出流中,完成后,继续往bufferBytes字节数组中写入,如此循环while ((length = is.read(bufferBytes)) != -1) {os.write(bufferBytes, 0, length);}os.flush();os.close();is.close();}

3.3.2 字符流

3.3.2.1 用字符流写文件

    public static void main(String[] args) throws IOException {File file = new File("d:/data_copy.txt");Writer writer = new FileWriter(file);String s = "你好啊你好啊你是谁啊你是老大么?";writer.write(s);writer.close();}

3.3.2.2 用字符流读文件

    public static void main(String[] args) throws IOException {File file = new File("d:/data.txt");Reader reader = new FileReader(file);char[] charArray = new char[(int) file.length()];int size = reader.read(charArray);System.out.println(new String(charArray).toString());reader.close();}

3.3.2.3 用字符流copy文件

   public static void copyFileByChar(String srcPath, String destPath) throws IOException {File src = new File(srcPath);File dest = new File(destPath);if (!src.isFile()) {throw new RuntimeException("拷贝的源文件不是文件类型,请检查源文件");}Reader is = new FileReader(src);Writer os = new FileWriter(dest);char[] bufferChars = new char[1024];int length = 0;while ((length = is.read(bufferChars)) != -1) {os.write(bufferChars, 0, length);}os.flush();os.close();is.close();}

3.3.3 缓冲流

3.3.3.1 用缓冲字节流copy文件

    public static void copyFile(String srcPath, String destPath) throws IOException {File src = new File(srcPath);File dest = new File(destPath);if (!src.isFile()) {throw new RuntimeException("拷贝的源文件不是文件类型,请检查源文件");}InputStream is = new BufferedInputStream(new FileInputStream(src));OutputStream os = new BufferedOutputStream(new FileOutputStream(dest));//设置一个缓存区,每次读取一个字节,从输入流中一个字节一个字节的,将读取的字节放入这下面这个字节数组中,如果字节数组满了,然后将此字节数组写入到输出流中byte[] bufferBytes = new byte[1024];int length = 0;//如果是-1,说明已经到文件结尾了,就暂停了;//如果不是-1,当bufferBytes字节数组满了以后,就将此字节数组写入到输出流中,完成后,继续往bufferBytes字节数组中写入,如此循环while ((length = is.read(bufferBytes)) != -1) {os.write(bufferBytes, 0, length);}os.flush();os.close();is.close();}

3.3.3.2 用缓冲字符流copy文件

    public static void copyFileByChar(String srcPath, String destPath) throws IOException {File src = new File(srcPath);File dest = new File(destPath);if (!src.isFile()) {throw new RuntimeException("拷贝的源文件不是文件类型,请检查源文件");}Reader is = new BufferedReader(new FileReader(src));Writer os = new BufferedWriter(new FileWriter(dest));char[] bufferChars = new char[1024];int length = 0;while ((length = is.read(bufferChars)) != -1) {os.write(bufferChars, 0, length);}os.flush();os.close();is.close();}

相关内容

热门资讯

在大吉订购APP订购交易亏损被...   近期,不少投资者反映在“大吉订购App”上投资白银、铂金等商品遭遇严重亏损。该平台宣称提供现货订...
铂银壹号APP商品订购交易亏损...   许多中小投资者误以为网上的“商品现货订购”是合规合法的理财渠道,殊不知这背后隐藏着巨大的合规风险...
兴鑫淘金APP贵金属订购交易亏...   白银、贵金属或其他商品类投资,除国家批准的正规期货交易场所及持牌期货公司外,市面上大量第三方交易...
铂银掘金APP无资质的违规平台...   铂银掘金等平台的投资者,往往是被“注册送现金”“充值返现券”“首单免亏”等广告话术吸引,进而下载...
八方淘金APP订购交易不合规,...   “八方淘金APP”“铂银掘金APP”“铂银壹号APP”等软件被指以“现货订购”为名,实际采用高杠...
在指尖订购APP订购商品亏损被...   指尖订购APP这类平台,表面是“订购交易”,实则是披着电商外衣的非法期货陷阱。绝大多数投资者被蒙...
在犀贝易购APP做商品订购交易...   市面上打着“现货投资”“贵金属交易”旗号的APP并不少,但真正合规、受监管的平台并不多。犀贝易购...
易达淘金APP虚假商品订购交易...   易达淘金APP存在严重的虚假宣传与违规交易行为。该平台打着“商品订购”的旗号,实则通过不合规的交...
大浪淘金APP白银订购亏损被骗...   大浪淘金APP最隐蔽的套路,在于其完全封闭的内盘交易系统。表面上,它宣称与国际贵金属市场接轨;实...
一品好购APP上订购白银出现亏...   一品好购APP原名“一品订购”,运营方为上海宝智未来信息技术有限公司。近期不少投资者反映在该平台...
九州订购APP贵金属订购投资骗...   九州订购APP正通过抖.音、快手、今日头条等平台大量投放投资广告,用“5元起投”“充值返现”“0...
坚锅淘金APP交易软件并不正规...   当前,市面上大量所谓的“现货商城订购”交易软件,早已偏离了正常的实物商品买卖,演变为高杠杆、高手...
斗金订购APP贵金属期货交易骗...   斗金订购APP的投资者往往被铺天盖地的广告宣传所诱导——注册即送现金、充值返现券等看似诱人的福利...
警惕!云启购APP违规经营,披...   "5元起投、充值返现、稳赚不赔"——这些诱人的广告语背后,可能是一个精心设计的金融陷阱。  近期...
量子淘金APP贵金属投资不合规...   "4元起投""充值返券""月入过万"——这些极具诱惑力的广告语在短视频平台、社交软件上铺天盖地。...
鑫汇智投APP贵金属商品订购骗...   鑫汇智投APP非法期货投资骗局,受害者在投资过程中根本不懂交易,也不去研究和验证这个平台是否正规...
矅光智策APP平台违规经营非法...   矅光智策APP对外宣称是“商城订购”“现货交易”,但查询其经营范围,并未显示具备开展现货期货交易...
黄金珠宝怎么选?内侧刻字都代表... 潮新闻客户端 记者 马焱 通讯员 任倩影 9月8日下午,“云游杭州 乐购金秋”——“浙城·浙放心”活...
原创 冰... 最近全球国债市场正在上演魔幻一幕: 美债、日债、欧债遭遇猛烈抛售,收益率冲到几十年新高,美国财政部都...
日韩股市开盘表现分化 上证报中国证券网讯 9月9日,日韩股市开盘表现分化,韩国综合指数开盘上涨0.26%,报6972.87...