zoukankan      html  css  js  c++  java
  • IO和NIO

    IO

    一、java io 概述

    什么是IO

    IO包括输入流和输出流,输入流指的是将数据以字符或者字节形式读取到内存 分为字符输入流和字符输入流

    输入流指的是从内存读取到外界 ,分为字符输入流和字节输出流

    Java IO即Java 输入输出系统。不管我们编写何种应用,都难免和各种输入输出相关的媒介打交道,其实和媒介进行IO的过程是十分复杂的,这要考虑的因素特别多,比如我们要考虑和哪种媒介进行IO(文件、控制台、网络),我们还要考虑具体和它们的通信方式(顺序、随机、二进制、按字符、按字、按行等等)。Java类库的设计者通过设计大量的类来攻克这些难题,这些类就位于java.io包中。

    什么是

    Java IO中,流是一个核心的概念。流从概念上来说是一个连续的数据流。你既可以从流中读取数据,也可以往流中写数据。流与数据源或者数据流向的媒介相关联。在Java IO中流既可以是字节流(以字节为单位进行读写),也可以是字符流(以字符为单位进行读写)

    二、Java IO类库的框架

    2.1 Java IO的类型

    虽然java IO类库庞大,但总体来说其框架还是很清楚的。从是读媒介还是写媒介的维度看,Java IO可以分为:

    1. 输入流:InputStream和Reader

    2. 输出流:OutputStream和Writer

    而从其处理流的类型的维度上看,Java IO又可以分为:

    1. 字节流:InputStream和OutputStream

    2. 字符流:Reader和Writer

    01File

       创建文件   删除文件 修改文件 删除文件信息

    02:字节流    InputStream            OutputStream     基类(父类)

    03:字符流    Reader                Writer

    04:缓冲流    BufferReader           BufferWriter  依赖于 Reader  Writer  

    05:二进制流  DataInputStream        DataOutputStream 依赖于InputStream OutputStream

    06:序例化    objectInputStream      ObjectOutputStream 依赖于InputStream OutputStream

    我们的程序需要通过InputStream或Reader从数据源读取数据,然后用OutputStream或者Writer将数据写入到目标媒介中。其中,InputStream和Reader与数据源相关联,OutputStream和writer与目标媒介相关联。 以下的图说明了这一点:

    三、Java IO的基本用法

    3.1 Java IO :字节流字节流对应的类应该是InputStreamOutputStream

    1,用字节流写文件

     1 package com.dzq;
     2 import java.io.*;
     3 /**
     4  * 字节流    InputStream            OutputStream
     5  */
     6 public class ByteDemo {
     7     public static void main(String[] args) {
     8         //创建输入流和输出流对象
     9         InputStream inputStream=null;
    10         OutputStream outputStream=null;
    11         try {
    12             inputStream=new FileInputStream("e:/aaa.txt");
    13             //true代表是否向文件拼接,不能删除之前的内容
    14             outputStream=new FileOutputStream("e:/aaa.txt",true);
    15            //向文件写入内容
    16             outputStream.write("54321".getBytes());
    17             //read方法0-255,如果流读到了最后,将返回-1
    18             int num=0;//int -1   字符串 null
    19             while ((num=inputStream.read())!=-1){
    20                 System.out.println((char)num);
    21             }
    22         } catch (Exception e) {
    23             e.printStackTrace();
    24         }
    25         try {
    26             inputStream.close();
    27             outputStream.close();
    28         } catch (IOException e) {
    29             e.printStackTrace();
    30         }
    31     }
    32 }
    用字节流写文件

    3.2 Java IO :字符流字符流对应的类应该是ReaderWriter

    2,用字符流文件

     1 package com.dzq;
     2 import java.io.*;
     3 /*
     4  * 字符流    Reader                Writer
     5  */
     6 public class CharDemo{
     7     public static void main(String[] args) {
     8         //创建字符流输出和输入
     9         Reader reader=null;
    10         Writer writer=null;
    11         try {
    12             reader=new FileReader("e:/aaa.txt");
    13             writer=new FileWriter("e:/aaa.txt",true);
    14             writer.write("我爱我家!");
    15             writer.write("我爱我家?");
    16             writer.write("我爱我家!!");
    17             writer.write("我爱我家??");
    18             writer.flush();
    19             writer.write("我爱我家!!!!");
    20             writer.close();
    21             //读取
    22             //创建一次性读取多个字符
    23             char[] bytes =new char[1024];
    24             int num=0;
    25             StringBuffer stringBuffer=new StringBuffer();
    26             while((num=reader.read(bytes))!=-1){
    27                 stringBuffer.append(bytes);
    28             }
    29             System.out.println(bytes);
    30         } catch (Exception e) {
    31             e.printStackTrace();
    32         }finally {
    33             try {
    34                 writer.close();
    35                 reader.close();
    36             } catch (IOException e) {
    37                 e.printStackTrace();
    38             }
    39         }
    40         }
    41 }
    用字符流写文件

    3.3 Java IO  :二进制流( DataInputStream DataOutputStream 依赖于 InputStream    OutputStream

     3,二进制流

     1 package com.dzq;
     2 import java.io.*;
     3 /*
     4  *二进制流  DataInputStream        DataOutputStream
     5  */
     6 public class DataDemo {
     7    public static void main(String[] args) {
     8        //创建输入流和输出流对象
     9         InputStream inputStream=null;
    10         OutputStream outputStream=null;
    11         DataInputStream dataInputStream=null;
    12         DataOutputStream dataOutputStream=null;
    13         try {
    14             //获取输入流
    15             inputStream=new FileInputStream("e:/aaa.txt");
    16             dataInputStream=new DataInputStream(inputStream);//封装
    17             //获取输出流
    18             outputStream=new FileOutputStream("e:/aaa.txt");
    19             dataOutputStream=new DataOutputStream(outputStream);
    20             //读取
    21             int num=0;
    22             while ((num=dataInputStream.read())!=-1){
    23                 dataOutputStream.write(num);//复制
    24             }
    25         } catch (Exception e) {
    26             e.printStackTrace();
    27         }finally {
    28             try {
    29                 dataOutputStream.close();
    30                 dataInputStream.close();
    31                 outputStream.close();
    32                 inputStream.close();
    33             } catch (IOException e) {
    34                 e.printStackTrace();
    35             }
    36         }
    37     }
    38 }
    二进制流

    3.4 Java IO(缓冲流BufferReader  BufferWriter 依赖于Reader Writer)

    例四:缓冲流

     1 package com.dzq;
     2 import java.io.*;
     3 /**
     4  *缓冲流    BufferReader           BufferWriter
     5  */
     6 public class BufferDemo {
     7     public static void main(String[] args) {
     8         //创建字符流输出和输入
     9         Reader reader = null;
    10         Writer writer = null;
    11         BufferedReader bufferReader=null;
    12         BufferedWriter bufferedWriter=null;
    13         try {
    14             //写入
    15             writer=new FileWriter("e:/aaa.txt") ;
    16            bufferedWriter=new BufferedWriter(writer);//封装
    17             bufferedWriter.write("我爱我家1");
    18             bufferedWriter.write("我爱我家2");
    19             bufferedWriter.write("我爱我家3");
    20             bufferedWriter.newLine();//换行
    21             bufferedWriter.write("我爱我家4");
    22             reader.close();
    23             bufferedWriter.close();//如果不关闭后两行出不来
    24             //读取
    25             reader=new FileReader("e:/aaa.txt") ;
    26             bufferReader=new BufferedReader(reader);//封装
    27             //拼接
    28             String line=null;
    29             StringBuffer stringBuffer=new StringBuffer();
    30             while((line=bufferReader.readLine())!=null){
    31                 stringBuffer.append(line);
    32             }
    33             System.out.println(stringBuffer.toString());
    34         } catch (Exception e) {
    35             e.printStackTrace();
    36         }finally {
    37             try {
    38                 bufferReader.close();
    39                 reader.close();
    40             } catch (IOException e) {
    41                 e.printStackTrace();
    42             }
    43         }
    44     }
    45     }
    缓冲流

    3.5 Java IO序列化和非序列化

    User类:

     1 package com.cd;
     2 import java.io.Serializable;
     3 public class User implements Serializable{
     4     public String username;
     5     public String password;
     6     public String getUsername() {
     7         return username;
     8     }
     9     public void setUsername(String username) {
    10         this.username = username;
    11     }
    12     public String getPassword() {
    13         return password;
    14     }
    15     public void setPassword(String password) {
    16         this.password = password;
    17     }
    18     public User(String username, String password) {
    19         this.username = username;
    20         this.password = password;
    21     }
    22     public User(){
    23     }
    24 }
    User

    写代码的固定区域:

     1 package com.cd;
     2 /**
     3  * 序列化和非序列化
     4  */
     5 import java.io.*;
     6 import java.util.Scanner;
     7 public  class ObjectDemo {
     8    static Scanner input=new Scanner(System.in);
     9     //创建输出流和输入流
    10     static  InputStream inputStream=null;
    11     static  OutputStream outputStream=null;
    12     static ObjectInputStream objectInputStream=null;
    13     static ObjectOutputStream objectOutputStream=null;
    14     public static void main(String[] args) {
    15            //登录
    16           Login();
    17           //注册
    18           register();
    19     }
    20     //注册
    21     private static void register() {
    22         User user =new User();
    23         System.out.println("请输入你的用户名");
    24         user.setUsername(input.next());
    25         System.out.println("请输入你的密码");
    26         user.setPassword(input.next());
    27         try {
    28          outputStream=new FileOutputStream("e:/aaa.txt");
    29            objectOutputStream=new ObjectOutputStream(outputStream);
    30             //把对象输出到文件中
    31             objectOutputStream.writeObject(user);
    32         } catch (Exception e) {
    33             e.printStackTrace();
    34         }finally {
    35             try {
    36                 objectOutputStream.close();
    37                 outputStream.close();
    38             } catch (IOException e) {
    39                 e.printStackTrace();
    40             }
    41         }
    42     }
    43     //登录
    44     private static void Login() {
    45         try {
    46             inputStream=new FileInputStream("e:/user.txt");
    47             objectInputStream=new ObjectInputStream(inputStream);
    48             //读取对象
    49             User user= (User) objectInputStream.readObject();
    50             System.out.println(user);
    51         } catch (Exception e) {
    52             e.printStackTrace();
    53         }finally {
    54             try {
    55                 objectInputStream.close();
    56                 inputStream.close();
    57             } catch (IOException e) {
    58                 e.printStackTrace();
    59             }
    60         }
    61     }
    62 }
    写代码的固定区域类

    3.6 Java IO :字节流转换为字符流InputStreamReader

     1 public static void convertByteToChar() throws IOException{
     2  File file= new File( "d:/test.txt"); 
     3 //获得一个字节流 InputStream is= new FileInputStream( file);
     4  //把字节流转换为字符流,其实就是把字符流和字节流组合的结果。
     5  Reader reader= new InputStreamReader( is);
     6  char [] byteArray= new char[( int) file.length()]; 
     7 int size= reader.read( byteArray); 
     8 System. out.println( "大小:"+size +";内容:" +new String(byteArray));
     9  is.close(); 
    10 reader.close();
    11  }
    字节流换为字符流

    四:使用IO写一个实例:

    功能简介: 

    创建文件

    删除文件 

    修改文件 

    创建文件夹

    删除文件夹 

    查询文件下所有的列表信息

    框架

    通用代码环节(首次)

    通用代码环节(首次)

    通用代码环节(首次)

     1 public class FileDemo
     2 {
     3     static  Scanner input =new Scanner(System.in);
     4     public static void main( String[] args )
     5     {
     6         System.out.println( "***********欢迎进入文件操作系统*******************" );
     7         System.out.println(" *******************1:创建文件*******************" );
     8         System.out.println( "*******************2:删除文件*******************" );
     9         System.out.println( "*******************3:修改文件*******************" );
    10         System.out.println( "*******************4:创建文件夹*******************" );
    11         System.out.println( "*******************5:删除文件夹*******************" );
    12         System.out.println( "*******************6:查询文件夹下所有的列表*******************" );
    13         int choose =input.nextInt();
    14         switch(choose){
    15             case 1://创建文件
    16                 createNewFile();
    17                 break;
    18             case 2://删除文件
    19                 deleteNewFile();
    20                 break;
    21             case 3://修改文件
    22                 updateNewFile();
    23                 break;
    24             case 4://创建文件夹
    25                 mkdirs();
    26                 break;
    27             case 5://删除文件夹
    28                 deletemkdirs();
    29                 break;
    30             case 6://查询文件夹下所有的列表
    31                 findFileList();
    32                 break;
    33         }
    34     }
    首次

    创建文件

     1 private static void createNewFile()
     2 {
     3     System.out.println("请输入文件的名称:(默认为E:/)");
     4     String fileName=input.next();
     5     //创建文件
     6     File file=new File("E:/"+fileName);//默认的路径
     7     if(file.exists()){
     8         System.out.println("该文件已存在!");
     9     }else{
    10         try {
    11             boolean flag =file.createNewFile();
    12             if(flag){
    13                 System.out.println("文件夹创建成功");
    14             }else{
    15                 System.out.println("文件夹创建失败");
    16             }
    17         } catch (IOException e) {
    18             e.printStackTrace();
    19         }
    20     }
    21 }
    创建文件

    删除文件

     1 private static void deleteNewFile()
     2 {
     3     System.out.println("请输入你要删除的文件名称:(默认为E:/)");
     4     String fileName=input.next();
     5     //创建File对象
     6     File file =new File("E:/"+fileName);
     7     if (file.exists()){
     8         boolean flag =file.delete();
     9         if(flag)
    10         {
    11             System.out.println("删除成功");
    12         }else{
    13             System.out.println("删除失败");
    14         }
    15     }else{
    16         System.out.println("该文件不存在");
    17     }
    18 }
    删除文件

    修改文件

     1 private static void updateNewFile()
     2 {
     3     System.out.println("请你输入需要修改的文件的名称:(默认为E:/)");
     4     String oldFileName=input.next();
     5     System.out.println("请你输入文件的新名称:(默认为E:/)");
     6     String newFileName=input.next();
     7     //创建File对象
     8     File oldFile=new File("E:/"+oldFileName);
     9     File NewFile=new File("E:/"+newFileName);
    10     if(oldFile.renameTo(NewFile)){
    11         System.out.println("修改成功");
    12     }else{
    13         System.out.println("修改失败");
    14     }
    15 }
    修改文件

    创建文件夹

     1 private static void mkdirs() {
     2     System.out.println("请输入你要创建的文件名称:(默认为E:/)");
     3     String fileName=input.next();
     4     //创建File对象
     5     File file =new File("E:/"+fileName);
     6     if (file.mkdirs()){
     7             System.out.println("创建成功");
     8         }else{
     9             System.out.println("创建失败");
    10         }
    11 }
    创建文件夹

    删除文件夹

    一:删除文件夹的方法先删除文件夹里面的东西在删除文件

     1 public static void delFolder(String folderPath) {
     2     try {
     3         delAllFile(folderPath); //删除完里面所有内容
     4         String filePath = folderPath;
     5         filePath = filePath.toString();
     6         java.io.File myFilePath = new java.io.File(filePath);
     7         myFilePath.delete(); //删除空文件夹
     8     } catch (Exception e) {
     9         e.printStackTrace();
    10     }
    11 }
    删除文件夹内部

    二:删除文件夹的方法

     1 public static boolean delAllFile(String path) {
     2     boolean flag = false;
     3     File file = new File(path);
     4     if (!file.exists()) {
     5         return flag;
     6     }
     7     if (!file.isDirectory()) {
     8         return flag;
     9     }
    10     String[] tempList = file.list();
    11     File temp = null;
    12     for (int i = 0; i < tempList.length; i++) {
    13         if (path.endsWith(File.separator)) {
    14             temp = new File(path + tempList[i]);
    15         } else {
    16             temp = new File(path + File.separator + tempList[i]);
    17         }
    18         if (temp.isFile()) {
    19             temp.delete();
    20         }
    21         if (temp.isDirectory()) {
    22             delAllFile(path  + tempList[i]);//先删除文件夹里面的文件
    23             delFolder(path  + tempList[i]);//再删除空文件夹
    24             flag = true;
    25         }
    26     }
    27     return flag;
    28 }
    删除文件夹内部和外部

    三:删除文件夹的终极方法

     1 private static void deletemkdirs() {
     2     System.out.println("请输入你要删除的文件夹名称:(默认为E:/)");
     3     String fileName=input.next();
     4     //创建File对象
     5     File file =new File("E:/"+fileName);
     6     if (file.exists()){
     7         boolean flag = delAllFile("E:/qqq");
     8         if(flag)
     9         {
    10             System.out.println("删除失败");
    11         }else{
    12             file.delete();
    13             System.out.println(" 删除成功");
    14         }
    15     }else{
    16         System.out.println("该文件不存在");
    17     }
    18 }
    删除文件终极方法

    NIO

    一:java nio 概述

    什么是NIO

    NIONew IO,这个库是在JDK1.4中才引入的。NIOIO有相同的作用和目的,但实现方式不同,NIO主要用到的是块,所以NIO的效率要比IO高很多。在Java API中提供了两套NIO,一套是针对标准输入输出NIO,另一套就是网络编程NIO

    java.nio 的核心的内容有:

    BufferChannel(SelectableChannel)Selector

    核心内容图示:

    注意点:

    :
    buffer
        缓冲区
       存储的是相同数据类型的数据集!
       本质是一个可以写入数据,并且从中读取数据的内存!
    01. position:
          写入或者读取的数据的当前指针
          最大值是: capacity-1
    02. limit:
         有多少数据可以写或者可以读
         write模式下,我们的limit和capacity的值一致!
         read模式下,我们的limit和write模 式下的position的值一致!
         position变成了0!
    03. capacity:缓冲区的最大容量

    1.1 Buffer的本质

    一个容器(数组实现)。一个初始化之后,大小就固定了的,底层用数组实现的,存储原始类型的容器(bytecharshortintlongfloatdouble)。每一个原始类型(boolean除外)对应一个子类,但是我们一般使用的都是 ByteBuffer,因为OS网络层最终传输的是字节byte:

    也就是说用java.nio编写非阻塞网络程序,在通过 Channel 发送和接受网络字节,一般都是使用 ByteBuffer,作为容器(数组)来暂时存储的。

    1.2 Buffer 的核心属性:mark 属性,mark() 函数,reset() 函数,它们是一组的,配合使用

    private int mark = -1;

    private int position = 0;

    private int limit;

    private int capacity;

    Buffer鉴别buffer limit position的值

    在默认的状态:

    1 package com.DX;
    2 import java.nio.IntBuffer;
    3 public class BufferDemo {
    4     public static void main(String[] args) {
    5         //创建一个容量为10 为int类型的缓冲区
    6         IntBuffer  buffer=IntBuffer.allocate(10);       System.out.println("capactity======>>"+buffer.capacity());       System.out.println("position======>>"+buffer.position());        System.out.println("limit======>>"+buffer.limit());
    在默认的状态:

    在写的状态:

    1 buffer.put(13);//转换成写的形式
    2 buffer.put(56);
    3 buffer.put(1343);
    4 buffer.put(13242);
    5 System.out.println("capactity======>>"+buffer.capacity());
    6 System.out.println("position======>>"+buffer.position());
    7 System.out.println("limit======>>"+buffer.limit());
    写的状态

    1 buffer.flip();//转换成读的形式   System.out.println("capactity======>>"+buffer.capacity());
    2 System.out.println("position======>>"+buffer.position());    System.out.println("limit======>>"+buffer.limit());
    3     //读取数据
    4     while(buffer.hasRemaining()){
    5         System.out.println(buffer.get());
    6     }
    7 }
    在读的状态:

    IONIO的区别

    图示:

    文字解释

    1、面向流与面向缓冲

         Java IONIO之间第一个最大的区别是,IO是面向流的,NIO是面向缓冲区的 Java IO面向流意味着每次从流中读一个或多个字节,直至读取所有字节,它们没有被缓存在任何地方。此外,它不能前后移动流中的数据。如果需要前后移动从流中读取的数据,需要先将它缓存到一个缓冲区。 Java NIO的缓冲导向方法略有不同。数据读取到一个它稍后处理的缓冲区,需要时可在缓冲区中前后移动。这就增加了处理过程中的灵活性。但是,还需要检查是否该缓冲区中包含所有您需要处理的数据。而且,需确保当更多的数据读入缓冲区时,不要覆盖缓冲区里尚未处理的数据。

    2、阻塞与非阻塞IO

         Java IO的各种流是阻塞的。这意味着,当一个线程调用read() write()时,该线程被阻塞,直到有一些数据被读取,或数据完全写入。该线程在此期间不能再干任何事情了。Java NIO的非阻塞模式,使一个线程从某通道发送请求读取数据,但是它仅能得到目前可用的数据,如果目前没有数据可用时,就什么都不会获取,而不是保持线程阻塞,所以直至数据变的可以读取之前,该线程可以继续做其他的事情。 非阻塞写也是如此。一个线程请求写入一些数据到某通道,但不需要等待它完全写入,这个线程同时可以去做别的事情。 线程通常将非阻塞IO的空闲时间用于在其它通道上执行IO操作,所以一个单独的线程现在可以管理多个输入和输出通道(channel)。

    3、选择器(Selectors

         Java NIO的选择器允许一个单独的线程来监视多个输入通道,你可以注册多个通道使用一个选择器,然后使用一个单独的线程来选择通道:这些通道里已经有可以处理的输入,或者选择已准备写入的通道。这种选择机制,使得一个单独的线程很容易来管理多个通道。

     

  • 相关阅读:
    vue嵌套路由
    不同的网络出现的报错
    yarn 创建react项目时出现错误
    vue-awsome-swiper竖向滚动出现空白
    SpringBoot路径映射
    ApplicationRunner接口
    CommandLineRunner接口
    springboot创建拦截器
    Cors跨域请求
    springboot自定义异常视图
  • 原文地址:https://www.cnblogs.com/3020815dzq/p/9261744.html
Copyright © 2011-2022 走看看