精华内容
下载资源
问答
  • IO操作

    千次阅读 2018-07-11 20:33:04
    一、简介IO流是用来处理设备之间的数据传输的,数据一般储存在设备上设备:硬盘,光盘,内存等等,内存是临时储存的Java对数据的操作是采用流的方式按照操作的数据分为:字节流和字符流暗照流向:输入流和输出流(相...

    一、简介


    IO流是用来处理设备之间的数据传输的,数据一般储存在设备上

    设备:硬盘,光盘,内存等等,内存是临时储存的

    Java对数据的操作是采用流的方式

    按照操作的数据分为:字节流和字符流

    暗照流向:输入流和输出流(相对于内存),读和写


    二、字节流


    Writer:写,输出流

    Reader:读,输入流

    字节流2个顶级父类InputStream(输入流)OutputStream(输出流),它们都是抽象类

    FileInputStream(文件输入流类)继承自InputStream(输入流),封装了对文件的读取操作,通过文件路径或者文件对象构造一个FileInputStream(文件输入流类)对象


    FileOutPutStream(文件输出流)继承自OutputStream(输出流),封装了对文件的写入操作,通过文件路径或者文件对象构造一个FileInputStream(文件输出流)对象。

    InputStream提供的方法主要有:

    序号

    方法

    功能说明

    1

    read( )

    读取一个字节

    2

    read(byte[] b)

    读取多个字节至数组b中

    3

    read(byte[] b, int off, int len)

    读取多个字节至数组从off开始的len个字节中

    4

    skip(long n)

    跳过n个字节

    5

    close

    关闭输入流

     

     

    OutputStream提供的方法主要有:

    序号

    方法

    功能说明

    1

    write(int n )

    写入一个字节(注意只写入低8位)

    2

    write (byte[] b)

    写入数组b中的全部字节

    3

    write (byte[] b, int off, int len)

    写入数组b中从off开始len个字节

    4

    flush( )

    刷新输出流,即强制输出(因有缓冲机制)

    5

    close

    关闭输入流

    FileInputStream(文件输入流类)继承自InputStream(输入流),封装了对文件的读取操作,通过文件路径或者文件对象构造一个FileInputStream(文件输入流类)对象。

    FileOutPutStream(文件输出流)继承自OutputStream(输出流),封装了对文件的写入操作,通过文件路径或者文件对象构造一个FileInputStream(文件输出流)对象。

    ObjectInputStream(对象输入流)ObjectOutPutStream(对象输出流)分别封装了其它类型数据的读、写操作,ObjectInputStream(对象输入流)构造函数传递需要InputStream(输入流)子类的对象,ObjectOutPutStream(对象输出流)构造函数传递需要OutPutStrea(输出量)子类的对象。

    ObjectInputStream(对象输入流)提供的方法主要有:

    序号

    方法

    功能说明

    1

    readInt、readFloat、readLong…

    读取基本类型数据

    2

    readObject

    读取引用类型数据(需反序列化)

     

    ObjectOutPutStream(对象输出流)提供的方法主要有:

    序号

    方法

    功能说明

    1

    writeInt、writeFloat、writeLong…

    写入基本类型数据

    2

    writeObject

    写入引用类型数据(需序列化)

    ObjectOutPutStream(对象输出流)向文件中输出123和“abc”,结果如下:

    所谓序列化就是将内存中的对象存储到外存上去。反序列化则反之,即将外存中的数据读入到内存中的对象中。
    ObjectInputStream(对象输入流)ObjectOutPutStream(对象输出流)分别封装了其它类型数据的读、写操作,ObjectInputStream(对象输入流)构造函数传递需要InputStream(输入流)子类的对象,ObjectOutPutStream(对象输出流)构造函数传递需要OutPutStrea(输出量)子类的对象。

    内存中的数据在关机后就不存在了,而外存的数据是可以永久保存的。比如游戏过程中的保存游戏,就是将某个时刻的游戏状态(比如生命值、金钱、等级等)数据保存到硬盘上;而读取游戏就是根据从文件中恢复游戏的状态。

    这些数据可能是一个对象,也可能是多个对象组成的复杂数据,如果逐个将原子数据写入到文件中去,不仅复杂,而且在写入和保存的步骤和数据应该严格一致,否则数据就会错位。

    序列化是将对象(不管多么复杂)整体写入文件中,将来也是整体读取,简化了读写操作。

    三、字符流


    Reader提供的方法主要有:

    序号

    方法

    功能说明

    1

    read( )

    读取一个字符

    2

    read(char []b)

    读取多个字节至数组b中

    3

    read(char []b, int off, int len)

    读取多个字节至数组从off开始的len个字节中

    4

    skip(long n)

    跳过n个字符

    5

    close

    关闭输入流

     

     

    Writer提供的方法主要有:

    序号

    方法

    功能说明

    1

    write(int n )

    写入一个字符(注意只写入低8位)

    2

    write (char []b)

    写入数组b中的全部字符

    3

    write (char []b, int off, int len)

    写入数组b中从off开始len个字符

    4

    write (String str)

    写入字符串中的全部字节

    5

    write (String str, int off, int len)

    写入字符串中从off开始len个字符

    6

    flush( )

    刷新输出流,即强制输出(因有缓冲机制)

    7

    close

    关闭输入流

     

    FileReadeer(文件阅读器)FileWriter(文件输出流)分别实现了Reader和Writer。

    缓冲机制用于应用程序和物理数据时降低应用程序对物理数据源访问的频次,从而提高了应用的运行性能。比如快递寄送点,并不是每收一个寄件就发送出去,而是收集到一定数量或一定时间后再整体发送。

    案例:

    C203_03_06_FileWriter

    package 第三章_IO操作.C203_03_05_FileWriter;
    
    import java.io.FileWriter;
    import java.io.IOException;
    
    public class Demo {
        publicstatic void main(String[] args)throws IOException{
            //FileWriter字符输出流
            FileWriterfw=new FileWriter("C:\\test5.txt");
            fw.write(97);
            fw.write("123");
            fw.close();
        }
    }

    C203_03_07_FileReader

    package 第三章_IO操作.C203_03_06_FileReader;
    
    import java.io.FileReader;
    
    public class Demo {
        publicstatic void main(String[] args)throws Exception{
            //FileReader字符流
            FileReaderfr=new FileReader("C:\\test.txt");
        int a=fr.read();
        char []str=new char[3];
        fr.read(str);
            System.out.println(a);
            System.out.println(str);
            fr.close();
        }
    }

    四、File类

    C203_03_08_缓冲机制

    package 第三章_IO操作.C203_03_08_缓冲机制;
    
    import java.io.BufferedOutputStream;
    import java.io.IOException;
    
    public class Demo {
        publicstatic void main(String[] args)throws IOException{
            BufferedOutputStream bos=new BufferedOutputStream(System.out,3);
            bos.write('a');
            bos.write('b');
            bos.write('c');
            bos.write('d');
            bos.write('e');
            bos.flush();
            bos.close();
        }
    }


    File类封装了对文件和目录的属性操作。目录也可以理解为一种特殊文件,下文中都统一称之为文件。

    序号

    方法

    功能说明

    1

    File(String path)

    根据路径构造一个文件

    2

    getName()

    获取文件名

    3

    exists()

    判断文件是否存在

    4

    isDirectory()

    判断是否为目录

    5

    isFile()

    判断是否为文件

    6

    length()

    获取文件的大小

    7

    close

    关闭输入流

    8

    delete()

    删除文件

    9

    list()

    列举文件或目录

    10

    listFiles()

    列举文件

    11

    mkdir()

    创建目录

    12

    renameTo

    重命名,实际上也可以实现移动

     

    案例:

    C203_03_09_文件操作

    package 第三章_IO操作.C203_03_07_文件操作;
    
    import java.io.File;
    
    public class Demo {
        publicstatic void main(String[] args)throws Exception{
            //File文件
            Filefile=new File("C:\\test6.txt");
            if(!file.exists()){//exists存在
                file.createNewFile();//createNewFile创建新文件
            }
            System.out.println(file.getName());
            System.out.println(file.length());
        }
    }

    C203_03_10_目录操作

    package 第三章_IO操作.C203_03_10_目录操作;
    
    import java.io.File;
    
    public class Demo {
        publicstatic void main(String[] args) {
            File dir=new File("C:/dir");
            if(!dir.exists()){
                dir.mkdir();//创建一个新的子目录
            }
            File dir1=new File("C:/dir/dir1");
            dir1.mkdir();
            File dir2=new File("C:/dir/dir2");
            dir2.mkdir();
    
            String []dirs=dir.list();
            for(Stringd:dirs){
                System.out.println(d);
            }
        }
    }


     





    展开全文
  • io操作

    千次阅读 2015-12-28 17:58:04
    高性能IO模型浅析 ...服务器端编程经常需要构造高性能的IO模型,常见的IO模型有...(1)同步阻塞IO(Blocking IO):即传统的IO模型。 (2)同步非阻塞IO(Non-blocking IO):默认创建的socket都是阻塞的,

    原文地址 http://www.cnblogs.com/fanzhidongyzby/p/4098546.html

    高性能IO模型浅析

     

    服务器端编程经常需要构造高性能的IO模型,常见的IO模型有四种:

    (1)同步阻塞IO(Blocking IO):即传统的IO模型。

    (2)同步非阻塞IO(Non-blocking IO):默认创建的socket都是阻塞的,非阻塞IO要求socket被设置为NONBLOCK。注意这里所说的NIO并非Java的NIO(New IO)库。

    (3)IO多路复用(IO Multiplexing):即经典的Reactor设计模式,有时也称为异步阻塞IO,Java中的Selector和Linux中的epoll都是这种模型。

    (4)异步IO(Asynchronous IO):即经典的Proactor设计模式,也称为异步非阻塞IO。

    同步和异步的概念描述的是用户线程与内核的交互方式:同步是指用户线程发起IO请求后需要等待或者轮询内核IO操作完成后才能继续执行;而异步是指用户线程发起IO请求后仍继续执行,当内核IO操作完成后会通知用户线程,或者调用用户线程注册的回调函数。

    阻塞和非阻塞的概念描述的是用户线程调用内核IO操作的方式:阻塞是指IO操作需要彻底完成后才返回到用户空间;而非阻塞是指IO操作被调用后立即返回给用户一个状态值,无需等到IO操作彻底完成。

    另外,Richard Stevens 在《Unix 网络编程》卷1中提到的基于信号驱动的IO(Signal Driven IO)模型,由于该模型并不常用,本文不作涉及。接下来,我们详细分析四种常见的IO模型的实现原理。为了方便描述,我们统一使用IO的读操作作为示例。

    一、同步阻塞IO

    同步阻塞IO模型是最简单的IO模型,用户线程在内核进行IO操作时被阻塞。

    1 同步阻塞IO

    如图1所示,用户线程通过系统调用read发起IO读操作,由用户空间转到内核空间。内核等到数据包到达后,然后将接收的数据拷贝到用户空间,完成read操作。

    用户线程使用同步阻塞IO模型的伪代码描述为:

    {

    read(socket, buffer);

    process(buffer);

    }

    即用户需要等待read将socket中的数据读取到buffer后,才继续处理接收的数据。整个IO请求的过程中,用户线程是被阻塞的,这导致用户在发起IO请求时,不能做任何事情,对CPU的资源利用率不够。

    二、同步非阻塞IO

    同步非阻塞IO是在同步阻塞IO的基础上,将socket设置为NONBLOCK。这样做用户线程可以在发起IO请求后可以立即返回。

     

    图2 同步非阻塞IO

    如图2所示,由于socket是非阻塞的方式,因此用户线程发起IO请求时立即返回。但并未读取到任何数据,用户线程需要不断地发起IO请求,直到数据到达后,才真正读取到数据,继续执行。

    用户线程使用同步非阻塞IO模型的伪代码描述为:

    {

    while(read(socket, buffer) != SUCCESS)

    ;

    process(buffer);

    }

    即用户需要不断地调用read,尝试读取socket中的数据,直到读取成功后,才继续处理接收的数据。整个IO请求的过程中,虽然用户线程每次发起IO请求后可以立即返回,但是为了等到数据,仍需要不断地轮询、重复请求,消耗了大量的CPU的资源。一般很少直接使用这种模型,而是在其他IO模型中使用非阻塞IO这一特性。

    三、IO多路复用

    IO多路复用模型是建立在内核提供的多路分离函数select基础之上的,使用select函数可以避免同步非阻塞IO模型中轮询等待的问题。

    图3 多路分离函数select

    如图3所示,用户首先将需要进行IO操作的socket添加到select中,然后阻塞等待select系统调用返回。当数据到达时,socket被激活,select函数返回。用户线程正式发起read请求,读取数据并继续执行。

    从流程上来看,使用select函数进行IO请求和同步阻塞模型没有太大的区别,甚至还多了添加监视socket,以及调用select函数的额外操作,效率更差。但是,使用select以后最大的优势是用户可以在一个线程内同时处理多个socket的IO请求。用户可以注册多个socket,然后不断地调用select读取被激活的socket,即可达到在同一个线程内同时处理多个IO请求的目的。而在同步阻塞模型中,必须通过多线程的方式才能达到这个目的。

    用户线程使用select函数的伪代码描述为:

    {

    select(socket);

    while(1) {

    sockets = select();

    for(socket in sockets) {

    if(can_read(socket)) {

    read(socket, buffer);

    process(buffer);

    }

    }

    }

    }

    其中while循环前将socket添加到select监视中,然后在while内一直调用select获取被激活的socket,一旦socket可读,便调用read函数将socket中的数据读取出来。

    然而,使用select函数的优点并不仅限于此。虽然上述方式允许单线程内处理多个IO请求,但是每个IO请求的过程还是阻塞的(在select函数上阻塞),平均时间甚至比同步阻塞IO模型还要长。如果用户线程只注册自己感兴趣的socket或者IO请求,然后去做自己的事情,等到数据到来时再进行处理,则可以提高CPU的利用率。

    IO多路复用模型使用了Reactor设计模式实现了这一机制。

    图4 Reactor设计模式

    如图4所示,EventHandler抽象类表示IO事件处理器,它拥有IO文件句柄Handle(通过get_handle获取),以及对Handle的操作handle_event(读/写等)。继承于EventHandler的子类可以对事件处理器的行为进行定制。Reactor类用于管理EventHandler(注册、删除等),并使用handle_events实现事件循环,不断调用同步事件多路分离器(一般是内核)的多路分离函数select,只要某个文件句柄被激活(可读/写等),select就返回(阻塞),handle_events就会调用与文件句柄关联的事件处理器的handle_event进行相关操作。

    5 IO多路复用

    如图5所示,通过Reactor的方式,可以将用户线程轮询IO操作状态的工作统一交给handle_events事件循环进行处理。用户线程注册事件处理器之后可以继续执行做其他的工作(异步),而Reactor线程负责调用内核的select函数检查socket状态。当有socket被激活时,则通知相应的用户线程(或执行用户线程的回调函数),执行handle_event进行数据读取、处理的工作。由于select函数是阻塞的,因此多路IO复用模型也被称为异步阻塞IO模型。注意,这里的所说的阻塞是指select函数执行时线程被阻塞,而不是指socket。一般在使用IO多路复用模型时,socket都是设置为NONBLOCK的,不过这并不会产生影响,因为用户发起IO请求时,数据已经到达了,用户线程一定不会被阻塞。

    用户线程使用IO多路复用模型的伪代码描述为:

    void UserEventHandler::handle_event() {

    if(can_read(socket)) {

    read(socket, buffer);

    process(buffer);

    }

    }

    {

    Reactor.register(new UserEventHandler(socket));

    }

    用户需要重写EventHandler的handle_event函数进行读取数据、处理数据的工作,用户线程只需要将自己的EventHandler注册到Reactor即可。Reactor中handle_events事件循环的伪代码大致如下。

    Reactor::handle_events() {

    while(1) {

    sockets = select();

    for(socket in sockets) {

    get_event_handler(socket).handle_event();

    }

    }

    }

    事件循环不断地调用select获取被激活的socket,然后根据获取socket对应的EventHandler,执行器handle_event函数即可。

    IO多路复用是最常使用的IO模型,但是其异步程度还不够“彻底”,因为它使用了会阻塞线程的select系统调用。因此IO多路复用只能称为异步阻塞IO,而非真正的异步IO。

    四、异步IO

    “真正”的异步IO需要操作系统更强的支持。在IO多路复用模型中,事件循环将文件句柄的状态事件通知给用户线程,由用户线程自行读取数据、处理数据。而在异步IO模型中,当用户线程收到通知时,数据已经被内核读取完毕,并放在了用户线程指定的缓冲区内,内核在IO完成后通知用户线程直接使用即可。

    异步IO模型使用了Proactor设计模式实现了这一机制。

    图6 Proactor设计模式

    如图6,Proactor模式和Reactor模式在结构上比较相似,不过在用户(Client)使用方式上差别较大。Reactor模式中,用户线程通过向Reactor对象注册感兴趣的事件监听,然后事件触发时调用事件处理函数。而Proactor模式中,用户线程将AsynchronousOperation(读/写等)、Proactor以及操作完成时的CompletionHandler注册到AsynchronousOperationProcessor。AsynchronousOperationProcessor使用Facade模式提供了一组异步操作API(读/写等)供用户使用,当用户线程调用异步API后,便继续执行自己的任务。AsynchronousOperationProcessor 会开启独立的内核线程执行异步操作,实现真正的异步。当异步IO操作完成时,AsynchronousOperationProcessor将用户线程与AsynchronousOperation一起注册的Proactor和CompletionHandler取出,然后将CompletionHandler与IO操作的结果数据一起转发给Proactor,Proactor负责回调每一个异步操作的事件完成处理函数handle_event。虽然Proactor模式中每个异步操作都可以绑定一个Proactor对象,但是一般在操作系统中,Proactor被实现为Singleton模式,以便于集中化分发操作完成事件。

    7 异步IO

    如图7所示,异步IO模型中,用户线程直接使用内核提供的异步IO API发起read请求,且发起后立即返回,继续执行用户线程代码。不过此时用户线程已经将调用的AsynchronousOperation和CompletionHandler注册到内核,然后操作系统开启独立的内核线程去处理IO操作。当read请求的数据到达时,由内核负责读取socket中的数据,并写入用户指定的缓冲区中。最后内核将read的数据和用户线程注册的CompletionHandler分发给内部Proactor,Proactor将IO完成的信息通知给用户线程(一般通过调用用户线程注册的完成事件处理函数),完成异步IO。

    用户线程使用异步IO模型的伪代码描述为:

    void UserCompletionHandler::handle_event(buffer) {

    process(buffer);

    }

    {

    aio_read(socket, new UserCompletionHandler);

    }

    用户需要重写CompletionHandler的handle_event函数进行处理数据的工作,参数buffer表示Proactor已经准备好的数据,用户线程直接调用内核提供的异步IO API,并将重写的CompletionHandler注册即可。

    相比于IO多路复用模型,异步IO并不十分常用,不少高性能并发服务程序使用IO多路复用模型+多线程任务处理的架构基本可以满足需求。况且目前操作系统对异步IO的支持并非特别完善,更多的是采用IO多路复用模型模拟异步IO的方式(IO事件触发时不直接通知用户线程,而是将数据读写完毕后放到用户指定的缓冲区中)。Java7之后已经支持了异步IO,感兴趣的读者可以尝试使用。

    本文从基本概念、工作流程和代码示例三个层次简要描述了常见的四种高性能IO模型的结构和原理,理清了同步、异步、阻塞、非阻塞这些容易混淆的概念。通过对高性能IO模型的理解,可以在服务端程序的开发中选择更符合实际业务特点的IO模型,提高服务质量。希望本文对你有所帮助。



    展开全文
  • 基本IO操作 、 文本数据IO操作

    万次阅读 2017-07-03 18:21:56
    1. 基本IO操作 1.1. InputStream与OutputStream 1.1.1. 输入与输出 我们编写的程序除了自身会定义一些数据信息外,经常还会引用外界的数据,或是将自身的数据发送到外界。比如,我们编写的程序想读取一个文本文件...

    1. 基本IO操作

    1.1. InputStream与OutputStream

    1.1.1. 输入与输出

    我们编写的程序除了自身会定义一些数据信息外,经常还会引用外界的数据,或是将自身的数据发送到外界。比如,我们编写的程序想读取一个文本文件,又或者我们想将程序中的某些数据写入到一个文件中。这时我们就要使用输入与输出。

    什么是输入:输入是一个从外界进入到程序的方向,通常我们需要“读取”外界的数据时,使用输入。所以输入是用来读取数据的。

    什么是输出:输出是一个从程序发送到外界的方向,通常我们需要”写出”数据到外界时,使用输出。所以输出是用来写出数据的。

    1.1.2. 节点流与处理流

    按照流是否直接与特定的地方 (如磁盘、内存、设备等) 相连,分为节点流和处理流两类。

    节点流:可以从或向一个特定的地方(节点)读写数据。

    处理流:是对一个已存在的流的连接和封装,通过所封装的流的功能调用实现数据读写。

    处理流的构造方法总是要带一个其他的流对象做参数。一个流对象经过其他流的多次包装,称为流的链接。

    1.1.3. InputStream与OutputStream常用方法

    InputStream是所有字节输入流的父类,其定义了基础的读取方法,常用的方法如下:

    1. int read()
    int read()
    

    读取一个字节,以int形式返回,该int值的”低八位”有效,若返回值为-1则表示EOF。

    1. int read(byte[] d)
    int read(byte[] d)
    

    尝试最多读取给定数组的length个字节并存入该数组,返回值为实际读取到的字节量。

    OutputStream是所有字节输出流的父类,其定义了基础的写出方法,常用的方法如下:

    1. void write(int d)
    void write(int d) 
    

    写出一个字节,写的是给定的int的”低八位”

    1. void write(byte[] d)
    void write(byte[] d)
    

    将给定的字节数组中的所有字节全部写出

    1.2. 文件流

    1.2.1. 创建FOS对象(重写模式)

    FileOutputStream是文件的字节输出流,我们使用该流可以以字节为单位将数据写入文件。

    构造方法:

    1. FileOutputStream(File file)
    FileOutputStream(File file)
    

    创建一个向指定 File 对象表示的文件中写入数据的文件输出流。

    例如:

    1. FIle file = new File("demo.dat");
    2. FileOutputStream fos = new FileOutputStream(file);
    FIle file = new File("demo.dat");
    FileOutputStream fos = new FileOutputStream(file); 
    

    构造方法:

    1. FileOutputStream(String filename):
    FileOutputStream(String filename):
    

    创建一个向具有指定名称的文件中写入数据的输出文 件流。

    例如:

    1. FileOutputStream fos = new FileOutputStream("demo.dat");
    FileOutputStream fos = new FileOutputStream("demo.dat"); 
    

    这里需要注意,若指定的文件已经包含内容,那么当使用FOS对其写入数据时,会将该文件中原有数据全部清除。

    1.2.2. 创建FOS对象(追加模式)

    通过上一节的构造方法创建的FOS对文件进行写操作时会覆盖文件中原有数据。若想在文件的原有数据之后追加新数据则需要以下构造方法创建FOS

    构造方法:

    1. FileOutputStream(File file,boolean append)
    FileOutputStream(File file,boolean append)
    

    创建一个向指定 File 对象表示的文件中写入数据的文件输出流。

    例如:

    1. File file = new File("demo.dat");
    2. FileOutputStream fos = new FileOutputStream(file,true);
    File file = new File("demo.dat");
    FileOutputStream fos = new FileOutputStream(file,true);
    

    构造方法:

    1. FileOutputStream(String filename,boolean append):
    FileOutputStream(String filename,boolean append):
    

    创建一个向具有指定名称的文件中写入数据的输出文 件流。

    例如:

    1. FileOutputStream fos = new FileOutputStream("demo.dat",true);
    FileOutputStream fos = new FileOutputStream("demo.dat",true);
    

    以上两个构造方法中,第二个参数若为true,那么通过该FOS写出的数据都是在文件末尾追加的。

    1.2.3. 创建FIS对象

    FileInputStream是文件的字节输入流,我们使用该流可以以字节为单位读取文件内容。

    FileInputStream有两个常用的构造方法:

    1. FileInputStream(File file):
    FileInputStream(File file):
    

    创建用于读取给定的File对象所表示的文件FIS

    例如:

    1. File file = new File("demo.dat");
    2. FileInputStream fis
    3.     = new FileInputStream(file);//创建一个用于读取demo.dat文件的输入流
    File file = new File("demo.dat");
    FileInputStream fis 
    	= new FileInputStream(file);//创建一个用于读取demo.dat文件的输入流
    

    另一个构造方法:

    1. FileInputStream(String name):
    FileInputStream(String name):
    

    创建用于读取给定的文件系统中的路径名name所指定的文件的FIS

    例如

    1. FileInputStream fis
    2.     //创建一个用于读取demo.dat文件的输入流
    3.     = new FileInputStream("demo");
    FileInputStream fis
    	//创建一个用于读取demo.dat文件的输入流
    	= new FileInputStream("demo");
    

    1.2.4. read()和write(int d)方法

    FileInputStream继承自InputStream,其提供了以字节为单位读取文件数据的方法read。

    1. int read()
    int read()
    

    从此输入流中读取一个数据字节,若返回-1则表示EOF(End Of File)

    FileOutputStream继承自OutputStream,其提供了以字节为单位向文件写数据的方法write。

    1. void write(int d)
    void write(int d)
    

    将指定字节写入此文件输出流。,这里只写给定的int值的”低八位”

    例如

    1. FileOutputStream fos = new FileOutputStream("demo.dat");
    2. fos.write('A');//这里要注意,char占用2个字节,但这里只写入了1个字节。
    FileOutputStream fos = new FileOutputStream("demo.dat");
    fos.write('A');//这里要注意,char占用2个字节,但这里只写入了1个字节。
    

    1.2.5. read(byte[] d)和write(byte[] d)方法

    FileInputStream也支持批量读取字节数据的方法:

    1. int read(byte[] b)
    int read(byte[] b)
    

    从此输入流中将最多 b.length 个字节的数据读入一个 byte 数组中 。

    FileOutputStream也支持批量写出字节数据的方法:

    1. void write(byte[] d)
    void write(byte[] d)
    

    将 b.length 个字节从指定 byte 数组写入此文件输出流中。

    例如:

    1. FileOutputStream fos = new FileOutputStream("demo.txt");
    2. byte[] data = "HelloWorld".getBytes();
    3. fos.write(data);//会将HelloWorld的所有字节写入文件。
    FileOutputStream fos = new FileOutputStream("demo.txt");
    byte[] data = "HelloWorld".getBytes();
    fos.write(data);//会将HelloWorld的所有字节写入文件。 
    

    将指定 byte 数组中从偏移量 off 开始的 len 个字节写入此文件输出流的方法:

    1. void write(byte[] d,int offset,int len)
    void write(byte[] d,int offset,int len)
    

    例如:

    1. FileOutputStream fos = new FileOutputStream("demo.txt");
    2. byte[] data = "HelloWorld".getBytes();
    3. fos.write(data,5,5);//只会将world这5个字节写入文件。
    FileOutputStream fos = new FileOutputStream("demo.txt");
    byte[] data = "HelloWorld".getBytes();
    fos.write(data,5,5);//只会将world这5个字节写入文件。 
    

    1.3. 缓冲流

    1.3.1. BOS基本工作原理

    与缓冲输入流相似,在向硬件设备做写出操作时,增大写出次数无疑也会降低写出效率,为此我们可以使用缓冲输出流来一次性批量写出若干数据减少写出次数来提高写 出效率。

    BufferedOutputStream缓冲输出流内部也维护着一个缓冲区,每当我们向该流写数据时,都会先将数据存入缓冲区,当缓冲区已满时,缓冲流会将数据一次性全部写出。

    1.3.2. BOS实现写出缓冲

    实现写出缓冲:

    1. public void testBos()throws Exception {
    2.     FileOutputStream fos = new FileOutputStream("demo.dat");
    3.     //创建缓冲字节输出流
    4.     BufferedOutputStream bos
    5.             = new BufferedOutputStream(fos);
    6. //所有字节被存入缓冲区,等待一次性写出
    7.     bos.write("helloworld".getBytes());
    8.     //关闭流之前,缓冲输出流会将缓冲区内容一次性写出
    9.     bos.close();
    10. }
    public void testBos()throws Exception {
    	FileOutputStream fos = new FileOutputStream("demo.dat");
    	//创建缓冲字节输出流
    	BufferedOutputStream bos
    			= new BufferedOutputStream(fos);
    //所有字节被存入缓冲区,等待一次性写出
    	bos.write("helloworld".getBytes());
    	//关闭流之前,缓冲输出流会将缓冲区内容一次性写出
    	bos.close();
    }
    

    1.3.3. BOS的flush方法

    使用缓冲输出流可以提高写出效率,但是这也存在着一个问题,就是写出数据缺乏即时性。有时我们需要在执行完某些写出操作后,就希望将这些数据确实写出,而非在缓冲区中保存直到缓冲区满后才写出。这时我们可以使用缓冲流的一个方法flush。

    1. void flush()
    void flush()
    

    清空缓冲区,将缓冲区中的数据强制写出。

    例如:

    1. BufferedOutputStream bos
    2.             = new BufferedOutputStream(
    3.                 new FileOutputStream("demo.dat")
    4.             );
    5. bos.write('a');//并没有向磁盘写出,而是写入到了BOS的缓存中
    6. bos.flush();//强制将缓存中的数据一次性写出,这时‘a’才会被写入磁盘
    7. bos.close();//实际上,close()方法在变比缓冲流前也调用了flush()
    BufferedOutputStream bos
    			= new BufferedOutputStream(
    				new FileOutputStream("demo.dat")
    			);
    bos.write('a');//并没有向磁盘写出,而是写入到了BOS的缓存中
    bos.flush();//强制将缓存中的数据一次性写出,这时‘a’才会被写入磁盘
    bos.close();//实际上,close()方法在变比缓冲流前也调用了flush()
    

    1.3.4. BIS基本工作原理

    在读取数据时若以字节为单位读取数据,会导致读取次数过于频繁从而大大的降低读取效率。为此我们可以通过提高一次读取的字节数量减少读写次数来提高读取的效率。

    BufferedInputStream是缓冲字节输入流。其内部维护着一个缓冲区(字节数组),使用该流在读取一个字节时,该流会尽可能多的一次性读取若干字节并存入缓冲区,然后逐一的将字节返回,直到缓冲区中的数据被全部读取完毕,会再次读取若干字节从而反复。这样就减少了读取的次数,从而提高了读取效率。

    BIS是一个处理流,该流为我们提供了缓冲功能。

    1.3.5. BIS实现输入缓冲

    使用缓冲流来实现文件复制:

    1. FileInputStream fis = new FileInputStream("java.zip");
    2. BufferedInputStream bis = new BufferedInputStream(fis);
    3. FileOutputStream fos = new FileOutputStream("copy_java.zip");
    4. BufferedOutputStream bos = new BufferedOutputStream(fos);
    5. int d = -1;
    6. while((d = bis.read())!=-1){
    7.     bos.write(d);
    8. }
    9. bis.close();//读写完毕后要关闭流,只需要关闭最外层的流即可
    10. bos.close();
    FileInputStream fis = new FileInputStream("java.zip");
    BufferedInputStream bis = new BufferedInputStream(fis);
    FileOutputStream fos = new FileOutputStream("copy_java.zip");
    BufferedOutputStream bos = new BufferedOutputStream(fos);
    int d = -1;
    while((d = bis.read())!=-1){
    	bos.write(d);
    }
    bis.close();//读写完毕后要关闭流,只需要关闭最外层的流即可
    bos.close();
    

    1.4. 对象流

    1.4.1. 对象序列化概念

    对象是存在于内存中的。有时候我们需要将对象保存到硬盘上,又有时我们需要将对象传输到另一台计算机上等等这样的操作。这时我们需要将对象转换为一个字节序列,而这个过程就称为对象序列化。相反,我们有这样一个字节序列需要将其转换为对应的对象,这个过程就称为对象的反序列化。

    1.4.2. 使用OOS实现对象序列化

    ObjectOutputStream是用来对对象进行序列化的输出流。

    其实现对象序列化的方法为:

    1. void writeObject(Object o)
    void writeObject(Object o)
    

    该方法可以将给定的对象转换为一个字节序列后写出。

    例如:

    1. Emp emp = new Emp("张三",12"男");
    2. FileOutputStream fos = new FileOutputStream("Emp.obj");
    3. ObjectOutputStream oos = new ObjectOutputStream(fos);
    4. oos.writeObject(emp);//将emp对象序列化后写入文件
    5. oos.close();
    Emp emp = new Emp("张三",12,"男");
    FileOutputStream fos = new FileOutputStream("Emp.obj");
    ObjectOutputStream oos = new ObjectOutputStream(fos);
    oos.writeObject(emp);//将emp对象序列化后写入文件
    oos.close();
    

    1.4.3. 使用OIS实现对象反序列化

    ObjectInputStream是用来对对象进行反序列化的输入流。

    其实现对象反序列化的方法为:

    1. Object readObject()
    Object readObject()
    

    该方法可以从流中读取字节并转换为对应的对象。

    例如:

    1. FileInputStream fis = new FileInputStream("Emp.obj");
    2. ObjectInputStream ois = new ObjectInputStream(fis);
    3. Emp emp = (Emp)ois.readObject();//将Emp对象从文件中读取并反序列
    4. ....
    5. ois.close();
    FileInputStream fis = new FileInputStream("Emp.obj");
    ObjectInputStream ois = new ObjectInputStream(fis);
    Emp emp = (Emp)ois.readObject();//将Emp对象从文件中读取并反序列
    ....
    ois.close();
    

    1.4.4. Serializable接口

    ObjectOutputStream在对对象进行序列化时有一个要求,就是需要序列化的对象所属的类必须实现Serializable接口。

    实现该接口不需要重写任何方法。其只是作为可序列化的标志。

    通常实现该接口的类需要提供一个常量serialVersionUID,表明该类的版本。若不显示的声明,在对象序列化时也会根据当前类的各个方面计算该类的默认serialVersionUID,但不同平台编译器实现有所不同,所以若向跨平台,都应显示的声明版本号。

    如果声明的类序列化存到硬盘上面,之后随着需求的变化更改了类别的属性(增加或减少或改名),那么当反序列化时,就会出现InvalidClassException,这样就会造成不兼容性的问题。 但当serialVersionUID相同时,它就会将不一样的field以type的预设值反序列化,可避开不兼容性问题。

    例如:

    1. public class Emp implements Serializable{
    2.     private static final long serialVersionUID = 1L;
    3.     private String name;
    4.     private int age;
    5.     private String gender;
    6.     //getter and setter and other
    7.     ...
    8. }
    public class Emp implements Serializable{
    	private static final long serialVersionUID = 1L;
    	private String name;
    	private int age;
    	private String gender;
    	//getter and setter and other
    	...
    }
    

    1.4.5. transient关键字

    对象在序列化后得到的字节序列往往比较大,有时我们在对一个对象进行序列化时可以忽略某些不必要的属性,从而对序列化后得到的字节序列”瘦身”。

    关键字 transient

    被该关键字修饰的属性在序列化时其值将被忽略

    例如:

    1. public class Emp implements Serializable{
    2.     private static final long serialVersionUID = 1L;
    3.     private String name;
    4.     private transient int age;//该属性在序列化时会被忽略
    5.     private String gender;
    6.     //getter and setter and other
    7.     ...
    8. }
    public class Emp implements Serializable{
    	private static final long serialVersionUID = 1L;
    	private String name;
    	private transient int age;//该属性在序列化时会被忽略
    	private String gender;
    	//getter and setter and other
    	...
    }
    

    2. 文件数据IO操作

    2.1. Reader和Writer

    2.1.1. 字符流原理

    Reader是所有字符输入流的父类,而Writer是所有字符输出流的父类。字符流是以字符(char)为单位读写数据的。一次处理一个unicode。字符流都是高级流,其底层都是依靠字节流进行读写数据的,所以底层仍然是基于字节读写数据的。

    2.1.2. 常用方法

    Reader的常用方法:

    1. int read()
    int read()
    

    读取一个字符,返回的int”值低16”位有效。

    1. int read(char[] chs)
    int read(char[] chs)
    

    从该流中读取一个字符数组length个字符并存入该数组,返回值为实际读取到的字符量。

    Writer的常用方法:

    1. void write(int c)
    void write(int c)
    

    写出一个字符,写出给定int值”低16”位表示的字符。

    1. void write(char[] chs)
    void write(char[] chs)
    

    将给定字符数组中所有字符写出。

    1. void write(String str)
    void write(String str)
    

    将给定的字符串写出

    1. void write(char[] chs,int offset,int len):
    void write(char[] chs,int offset,int len):
    

    将给定的字符数组中从offset处开始连续的len个字符写出

    2.2. 转换流

    2.2.1. 字符转换流原理

    InputStreamReader:字符输入流, 使用该流可以设置字符集,并按照指定的字符集从流中按照该编码将字节数据转换为字符并读取。

    OutputStreamWriter:字符输出流,使用该流可以设置字符集,并按照指定的字符集将字符转换为对应字节后通过该流写出。

    2.2.2. 指定字符编码

    InputStreamReader的构造方法允许我们设置字符集:

    1. InputStreamReader(InputStream in,String charsetName)
    InputStreamReader(InputStream in,String charsetName)
    

    基于给定的字节输入流以及字符编码创建ISR

    1. InputStreamReader(InputStream in)
    InputStreamReader(InputStream in)
    

    该构造方法会根据系统默认字符集创建ISR

    OutputStreamWriter:的构造方法:

    1. OutputStreamWriter(OutputStream out,String charsetName)
    OutputStreamWriter(OutputStream out,String charsetName)
    

    基于给定的字节输出流以及字符编码创建OSW

    1. OutputStreamWriter(OutputStream out)
    OutputStreamWriter(OutputStream out) 
    

    该构造方法会根据系统默认字符集创建OSW

    2.2.3. 使用OutputStreamWriter

    1. ...
    2. public void testOutput() throws IOException{
    3.     FileOutputStream fos
    4.         = new FileOutputStream("demo.txt");
    5.     OutputStreamWriter writer
    6.         //这里使用的字符编码为UTF-8
    7.         = new OutputStreamWriter(fos,"UTF-8");        
    8.     String str = "大家好!";//UTF-8中文为3个字节,英文符号占1个字节
    9.     writer.write(str);//写出后该文件大小应该为10字节
    10.     writer.close();
    11. }
    12. ...
    ...
    public void testOutput() throws IOException{
    	FileOutputStream fos 
    		= new FileOutputStream("demo.txt");
    	OutputStreamWriter writer
    		//这里使用的字符编码为UTF-8
    		= new OutputStreamWriter(fos,"UTF-8");		
    	String str = "大家好!";//UTF-8中文为3个字节,英文符号占1个字节
    	writer.write(str);//写出后该文件大小应该为10字节
    	writer.close();
    }
    ... 
    

    2.2.4. 使用InputStreamReader

    1. ...
    2. public void testInput() throws IOException{
    3.     FileInputStream fis
    4.         = new FileInputStream("demo.txt");
    5.     /*
    6.     * 这里设置了字符编码为GBK
    7.     * 之后再通过ISR读取demo.txt文件时
    8.     * 就使用GBK编码读取字符了
    9.     */
    10.     InputStreamReader reader
    11.         = new InputStreamReader(fis,"GBK");
    12.     int c = -1;
    13.     while((c = reader.read()) != -1){
    14.         System.out.print((char)c);
    15.     }
    16.     reader.close();
    17. }
    18. ...
    ...
    public void testInput() throws IOException{
    	FileInputStream fis 
    		= new FileInputStream("demo.txt");
    	/*
    	*  这里设置了字符编码为GBK
    	*  之后再通过ISR读取demo.txt文件时
    	*  就使用GBK编码读取字符了
    	*/
    	InputStreamReader reader
    		= new InputStreamReader(fis,"GBK");
    	int c = -1;
    	while((c = reader.read()) != -1){
    		System.out.print((char)c);
    	} 
    	reader.close();
    } 
    ...
    
    展开全文
  • Kotlin IO操作

    万次阅读 2017-03-21 17:06:25
    前段时间学习了一点内容,写了一...Kotlin的IO操作都在kotlin.io包下。Kotlin的原则就是Java有的就直接利用,没有的才自己想办法写。因此Kotlin的IO操作主要是依靠扩展方法,在原有的Java类上添加功能实现的。这一点倒

    前段时间学习了一点内容,写了一篇Groovy开发工具包。我当时就在想Kotlin怎么没有好用的文件操作API呢?后来我发现我太傻了,Kotlin这么好用的语言怎么可能没有自己的文件API呢?

    Kotlin的IO操作都在kotlin.io包下。Kotlin的原则就是Java有的就直接利用,没有的才自己想办法写。因此Kotlin的IO操作主要是依靠扩展方法,在原有的Java类上添加功能实现的。这一点倒是和Groovy有点像。

    下面介绍的很多方法都有一个Charset参数,可以直接要使用的字符集,默认是UTF-8。如果需要其他的字符集,用这个参数指定就行了。

    终端IO

    如果学过C++的同学可能会对Java超长的输出语句System.out.println()所震惊。同样的工作在C++里面只需要简单的cout<<就可以完成。

    幸好,在Kotlin里面很简单,只需要使用println或者print这两个全局函数即可。我们不再需要冗长的前缀。

    从终端读取数据也很简单,最基本的方法就是全局函数readLine,它直接从终端读取一行作为字符串。如果需要更进一步的处理,可以使用Kotlin提供的各种字符串处理函数来处理和转换字符串。

    文件IO

    Kotlin为java.io.File提供了大量好用的扩展方法,详细的扩展方法见这里java.io.File。这里我就跳着说几个最常用最好用的吧。

    首先先看读取文件。如果需要简单读取一个文件,可以使用readText()方法,它直接返回了整个文件内容。如果希望按行读取,还可以使用readLines()方法,这会返回一个行字符串数组,我们可以随意操作。如果希望直接操作字节数组,那就使用readBytes()。如果想使用传统的Java方式,Kotlin也能满足你。

    fun readFile() {
        val filename = """C:\Windows\System32\drivers\etc\hosts"""
        val file = File(filename)
        val contents = file.readText()
        println(contents)
    
        //大写前三行
        file.readLines().take(3).forEach {
            println(it.toUpperCase())
        }
    
        //直接处理行
        file.forEachLine(action = ::println)
    
        //读取为bytes
        val bytes: ByteArray = file.readBytes()
        println(bytes.joinToString(separator = ""))
    
        //直接处理Reader或InputStream
        val reader: Reader = file.reader()
        val inputStream: InputStream = file.inputStream()
        val bufferedReader: BufferedReader = file.bufferedReader()
    }

    和读取文件类似,写入文件也很简单。我们可以写入字符串,也可以写入字节流。还可以直接使用Java的Writer或者OutputStream。

    fun writeFile() {
        val currentDir = System.getProperty("user.dir") + "\\out"
        val file = File(currentDir, "hehe.txt")
        file.writeText("呵呵呵哈哈哈")
        println(file.readText())
    
        file.writeBytes(byteArrayOf(12, 56, 83, 57))
        println(file.readText())
    
        //追加方式写入字节或字符
        file.appendBytes(byteArrayOf(93, 85, 74, 93))
        file.appendText("吼啊")
        println(file.readText())
    
        //直接使用writer和outputstream
        val writer: Writer = file.writer()
        val outputStream: OutputStream = file.outputStream()
        val printWriter: PrintWriter = file.printWriter()
    
    }

    遍历文件树

    和Groovy一样,Kotlin也提供了方便的功能来遍历文件树。遍历文件树需要调用扩展方法walk()。它会返回一个FileTreeWalk对象,它有一些方法用于设置遍历方向和深度,详情参见FileTreeWalk

    下面的例子遍历了指定文件夹下的所有可执行文件。

    fun traverseFileTree() {
        val systemDir = File("""C:\Windows""")
        val fileTree: FileTreeWalk = systemDir.walk()
        fileTree.maxDepth(1)
                .filter { it.isFile }
                .filter { it.extension == "exe" }
                .forEach(::println)
    
    }

    网络IO

    Kotlin为java.net.URL增加了两个扩展方法,readBytesreadText。我们可以方便的使用这两个方法配合正则表达式实现网络爬虫的功能。

    下面第一个例子简单的获取了百度首页的源代码。第二个例子先获取了必应首页图片的XML格式信息,然后通过正则表达式和分组获取图片的相对URL并组合出实际URL,然后调用readBytes()方法读取到字节流并写入文件。

    fun readFromNet() {
        //返回百度首页
        val baidu = URL("http://www.baidu.com")
        val contents = baidu.readText()
        //println(contents)
    
        //获取必应首页图片并保存
        //获取XML格式图片信息
        val bing = URL("http://www.bing.com/HPImageArchive.aspx?format=xml&idx=0&n=1&mkt=en-US")
        val texts = bing.readText()
        //获取url地址和文件名
        val regex = Regex("""<url>(.*)</url>""")
        val result = regex.find(texts)
        val imageUrl = "http://www.bing.com" + result!!.groupValues[1]
        val filename = imageUrl.substring(imageUrl.lastIndexOf('/'))
        //写入文件
        val output = File(System.getProperty("user.dir") + "\\out", filename)
        val requestUrl = URL(imageUrl)
        output.writeBytes(requestUrl.readBytes())
    
    }

    在项目相应文件夹下我们可以看到下载好的图片。

    下载好的图片

    展开全文
  • Scala IO操作

    千次阅读 2016-04-09 23:24:48
    Scala IO操作         Scala IO操作有执行常用的文件处理任务,比如从文件中读取所有行或单词,或者读取包含数字的文件等。   读取行   要读取文件中所有行,可以调用scala.io.Source对象的...
  • GO语言IO操作

    千次阅读 2017-11-10 16:39:26
    GO语言IO操作
  • RapidIO操作协议

    千次阅读 2017-08-17 21:08:27
    RapidIO操作协议 逻辑层协议定义了 10操作协议和相应的数据包格式、门铃的格式、流量控制。 I/O操作协议在互连结构中利用请求/响应事务来完成。请求和相应对穿越RapidIO交换结构运行,但当事务穿越交换结构时RapidIO...
  • python的IO操作

    千次阅读 2018-08-13 17:16:11
    IO操作 IO也就是我们说的Input/Output,也就是输入和输出。我们的程序在运行过程中所有的数据都是驻留在内存当中,有的时候我们需要将内存的数据写到磁盘中,这时候就要用到磁盘IO,有的时候我们需要网络和其他...
  • linux文件IO操作

    2016-12-13 15:51:29
    说起linux编程来,甚至包括其他系统的编程,很大一部分都是处理IO操作了。特别是在linux系统上,由于一起都是文件(fd)的思想,更是扩大了文件IO的范畴。比如磁盘上文件的IO,网络IO,终端IO,管道IO等等。这些IO...
  • java安全编码指南之:文件IO操作

    万次阅读 2020-10-27 10:47:35
    对于文件的IO操作应该是我们经常会使用到的,因为文件的复杂性,我们在使用File操作的时候也有很多需要注意的地方,下面我一起来看看吧。
  • IO操作 IO异常处理

    千次阅读 2012-10-03 12:23:21
    /* * 程序头部注释开始 * 程序的版权和版本声明部分 * Copyright (c) 2011, 烟台大学计算机学院学生 * All rights reserved....* 文件名称:IO操作 IO异常处理 * 作 者:薛广晨 * 完成日期:2011
  • Java IO操作详解

    千次阅读 2016-10-26 13:03:01
    在Java编程中,IO(输入输出)是重要的组成部分,Java应用常常...所有的IO操作都在java.io包之中进行定义,而且整个java.io包实际上就是五个类和一个接口: (1)五个类:File、InputStream、OutputStream、Reader、
  • Kotlin方便快捷的IO操作

    千次阅读 2017-08-16 18:49:09
    Kotlin的IO操作都在kotlin.io包下。Kotlin的一个原则就是Java有的就直接利用,没有的就在原有的Java类上添加功能实现。因此Kotlin的IO操作除了传统的java方式,还依靠扩展方法提供了许多简便操作方法。文件IO文件...
  • IO操作和DMA、RDMA

    千次阅读 2020-02-03 22:11:07
    用户进程想要执行IO操作时(例如想要读磁盘数据、向磁盘写数据、读键盘的输入等等),由于用户进程工作在用户模式下,它没有执行这些操作的权限,只能通过发起对应的系统调用请求操作系统帮忙完成这些操作。...
  • io操作和cpu密集型操作

    千次阅读 2017-10-17 18:08:16
    python中不适合处理cpu密集型操作,因为cpu密集型操作就像是超市运货,货到了超市门口运进超市,比较消耗cpu性能,而...而io操作,就像是超市找多个厂家订货,因为送货需要时间,而订货时间很短,所以io操作消耗不大
  • 对CPU的IO操作的理解

    2020-03-31 22:42:20
    什么是io操作 读写cpu寄存器,cache之外的设备叫做cpu的io操作,如内存,硬盘,网卡,但是读写内存很快,一般不将读写内存叫做io操作
  • Java中的IO操作

    千次阅读 2018-03-23 21:46:47
    IO 操作是我以前不太理解的操作。总是觉得很神奇,然后一脸懵逼。今天终于鼓起勇气,认真的学习...我们需要将硬盘的文件数据读入到内存中,再将数据从内存输出到硬盘中,所以我们就有了IO操作。i和o是分别代表(inpu...
  • 康耐视智能相机IO操作笔记

    千次阅读 2020-05-10 14:57:21
    在视觉学习中,IO的操作是非常有必要的,在康耐视智能相机中IO操作记录如下: 1.相机IO触发拍照,这个不用自己去设置,IO线按照说明书接线即可。 2.相机IO输出信号给其他设备使用: 最常见的场景是,相机拍照后...
  • Java IO操作——文件操作类File的使用

    千次阅读 2016-07-14 15:46:20
    学习目标 掌握File类的使用 可以使用File类中的方法对文件进行操作。 在整个Java的学习中,个人感觉学习较为困难的... 所有的IO操作都保存在java.io包中。 File类 在整个io包中,唯一表示与文件本身有关的类就是Fi
  • linux系统中的IO操作

    千次阅读 2016-10-22 19:39:32
    同步IO分为阻塞IO、非阻塞IO、信号驱动的IO和多路转接IO。 阻塞IO: 一直阻塞进程直到完成IO操作。...当设置打开文件描述字O_ASYNC标志是可以用于信号驱动的IO操作,也可以用过fcntl()改变文件标签,当文件进行IO操作
  • Kotlin和Java中的IO操作

    千次阅读 2018-04-07 12:19:51
    Kotlin的特性 1.Kotlin提供了非常多,File、Stream、Reader、Writer的...一、首先来看看繁琐的JavaIO操作,来读取一个文件 package cn.kotliner.java.io; import java.io.*; /** * Created by wangdong * Java...
  • java中的IO操作总结

    千次阅读 2019-02-22 14:30:59
    java中的IO操作 在java中IO涉及的范围比较大,本文主要针对文件内容的读写 对于文件内容的操作主要分为两大类: 字符流:有两个抽象类 writer Reader  其对应子类FileWriter和FileReader可实现文件的读写...
  • 贴出代码 1.线程循环发送 public void PortListenThread() { while (true) ...//报错:由于IO线程退出或应用程序请求,已中止IO操作。 } catch (Exception a) { MessageBox.Show(a.Message); }
  • Python 12:Python 文件io操作模块

    千次阅读 2016-08-02 22:11:45
    Python 文件io操作模块介绍IO操作是每种程序设计语言都会设计的模块,python的io操作设计的和C语言很类似,比较简便实用.反观Java语言对于io操作设计的模块就比较抽象和灵活,这也导致java的io学习成本远比Python语言的...
  • JAVA 基础 (四) IO操作

    千次阅读 2014-11-25 11:44:02
    java.io操作是java基础中的基础,如果没有io操作程序都不会运行起来,所以,又回顾了一下java.io操作的内容,里面的对象序列化是J2EE的基础,是java中分布式部署和调用实现的基础,还有很有对文件系统、对网络资源的...
  • Java基础: IO操作

    千次阅读 热门讨论 2014-04-27 18:38:55
    最近抽了点时间回顾了java基础,昨天看了java的IO操作,把大致的总结写在这里。  Java的IO操作主要是数据的输入、输出操作和文件管理,输入输出操作可以包括控制台、文件的输入输出和流的输入输出,流的输入输出...
  • Qt 笔记:Qt中的IO操作

    千次阅读 2018-09-14 17:51:44
    Qt中IO操作的处理方式 -Qt通过统一的接口简化了文件与外部设备的操作方式 -Qt中的文件被看做一种特殊的外部设备 -Qt中的文件操作与外部设备的操作相同 IO操作中的关键函数接口 -打开设备:bool open(OpenMode ...
  • LINUX 高级IO操作

    千次阅读 2011-12-23 15:49:36
    LINUX 高级IO操作 一 知识点非常重要 二 非阻塞的IO  系统调用: 低速系统调用,其他系统调用  低速系统调用的类别:  1)读网络设备,终端,管道等,暂时没有数据输入,则阻塞读操作  2)同上的写操作...
  • java-IO操作性能对比

    千次阅读 2014-06-05 08:31:20
    在java标准IO操作中,InputStream和OutputStream提供基于流的IO操作,以字节为处理单位;Reader和Writer实现了Buffered缓存,以字符为处理单位。 从Java1.4开始,增加NIO(New IO),增加缓存Buffer和通道Channel,...
  • MySQL数据库的IO操作

    千次阅读 2013-11-06 16:01:11
    淘宝丁奇分享的PPT:MySQL数据库的IO操作,详细分享了四块的内容,并且告诉大家如何调整MySQL数据库IO操作相关的参数,给出了详细的选择策略,现替其整理成文章分享与此。 PPT内容提纲: 1.MySQL的文件及简介 ...

空空如也

空空如也

1 2 3 4 5 ... 20
收藏数 84,500
精华内容 33,800
关键字:

io操作