三种io方式,有哪几种io控制方式其主要工作原理如何

1 , 有哪几种io控制方式其主要工作原理如何程序I/O :CPU 被I/O 输入输出无限等待 浪费资源---------->中断I/O:仅当输入输出完毕,CPU才处理,但中断次数还是太多,因为会经常输入输出---------->DMA :输入输出以块来中断 , CPU仅在输入输出了一大堆数据(一个块)才处理一次,没怎么被I/O所拖累--------->通道:我记得是已经把CPU完全从I/O中解放出来了 。总之关系就是 想让CPU从I/O 从解放出来而不断发展的结果 。
2,io系统的输入输出方式有哪几种各具什么特点CPU与外设之间传输数据的控制方式通常有三种:程序方式、中断方式和DMA方式 。程序方式:指用输入/输出指令,来控制信息传输的方式,是一种控制方式 , 根据程序控制的方法不同,又可以分为无条件传送方式和条件传送方式 。无条件传送方式接口简单,适用于那些能随时读写的设备 。条件传送方式(查询方式) 的特点是接口电路简单,CPU利用率低(程序循环等待),接口需向CPU提供查询状态 。适用于CPU不太忙,传送速度要求不高的场合 。要求各种外设不能同时工作,外设处于被动状态 。中断方式:当外设准备好时 , 由外设通过接口电路向CPU发出中断请求信号,CPU在允许的情况下,暂停执行当前正在执行的程序,响应外设中断,转入执行相应的中断服务子程序,与外设进行一次数据传送,数据传送结束后,CPU返回继续执行原来被中断的程序 。其特点是CPU的利用率高,外设具有申请CPU中断的主动权,CPU和外设之间处于并行工作状态 。但中断服务需要保护断点和恢复断点(占用存储空间,降低速度), CPU和外设之间需要中断控制器 。适用于CPU的任务较忙、传送速度要求不高的场合 , 尤其适合实时控制中的紧急事件处理 。存储器直接存取方式(DMA):外设利用专用的接口(DMA控制器)直接与存储器进行高速数据传送 , 并不经过CPU(CPU不参与数据传送工作),总线控制权不在CPU处,而由DMA 控制器控制 。其特点是接口电路复杂,硬件开销大 。大批量数据传送速度极快 。适用于存储器与存储器之间、存储器与外设之间的大批量数据传送的场合 。你说呢...
3,在单片机中控制IO操作有几种方一般使用寄存器读写,也就是字节读写,还有就是位操作 。cpu与外设之间传输数据的控制方式通常有三种:程序方式、中断方式和dma方式 。程序方式:指用输入/输出指令 , 来控制信息传输的方式,是一种软件控制方式,根据程序控制的方法不同,又可以分为无条件传送方式和条件传送方式 。无条件传送方式接口简单,适用于那些能随时读写的设备 。条件传送方式(查询方式) 的特点是接口电路简单,cpu利用率低(程序循环等待),接口需向cpu提供查询状态 。适用于cpu不太忙,传送速度要求不高的场合 。要求各种外设不能同时工作,外设处于被动状态 。中断方式:当外设准备好时 , 由外设通过接口电路向cpu发出中断请求信号,cpu在允许的情况下,暂停执行当前正在执行的程序,响应外设中断,转入执行相应的中断服务子程序 , 与外设进行一次数据传送,数据传送结束后,cpu返回继续执行原来被中断的程序 。其特点是cpu的利用率高,外设具有申请cpu中断的主动权,cpu和外设之间处于并行工作状态 。但中断服务需要保护断点和恢复断点(占用存储空间,降低速度),cpu和外设之间需要中断控制器 。适用于cpu的任务较忙、传送速度要求不高的场合 , 尤其适合实时控制中的紧急事件处理 。存储器直接存取方式(dma):外设利用专用的接口(dma控制器)直接与存储器进行高速数据传送 , 并不经过cpu(cpu不参与数据传送工作),总线控制权不在cpu处 , 而由dma 控制器控制 。其特点是接口电路复杂,硬件开销大 。大批量数据传送速度极快 。适用于存储器与存储器之间、存储器与外设之间的大批量数据传送的场合 。各家的MCU有各自操作方法 。主要还是看编译器,有些是自带支持位操作的,有些则要自己写 , 大多都可以直接位操作,我用过的 , 51、PIC都有位操作(C语言),但AVR的就得自己写 。【三种io方式,有哪几种io控制方式其主要工作原理如何】
4,有哪些IO控制方式各用于什么场合有哪些I/O控制方式?各用于什么场合?程序I/O方式(适用于结构简单 , 只需少量硬件的电路) 中断驱动I/O控制方式(适用于高效的场合,例如办公室) 直接存储器访问DMA I/O控制方式(适用于无须CPU介入的控制器来控制内存与外设之间的数据交流的场合) I/O通道控制方式(适用于以字节为单位的干预 , 同时实现CPU,通道和I/O设备三者并行操作的场合)[编辑本段]1.I/O (input/output):输入输出端口就是输入输出地址 。每个设备都会有一个专用的I/O地址,用来处理自己的输入输出信息 。CPU与外部设备、存储器的连接和数据交换都需要通过接口设备来实现 , 前者被称为I/O接口,而后者则被称为存储器接口 。存储器通常在CPU的同步控制下工作,接口电路比较简单;而I/O设备品种繁多 , 其相应的接口电路也各不相同,因此 , 习惯上说到接口只是指I/O接口 。一、I/0接口的概念1、接口的分类I/O接口的功能是负责实现CPU通过系统总线把I/O电路和 外围设备联系在一起,按照电路和设备的复杂程度 , I/O接口的硬件主要分为两大类:?。?)I/O接口芯片这些芯片大都是集成电路 , 通过CPU输入不同的命令和参数,并控制相关的I/O电路和简单的外设作相应的操作,常见的接口芯片如定时/计数器、中断控制器、DMA控制器、并行接口等 。?。?)I/O接口控制卡有若干个集成电路按一定的逻辑组成为一个部件,或者直接与CPU同在主板上,或是一个插件插在系统总线插槽上 。按照接口的连接对象来分 , 又可以将他们分为串行接口、并行接口、键盘接口和磁盘接口等 。2、接口的功能由于计算机的外围设备品种繁多,几乎都采用了机电传动设备,因此,CPU在与I/O设备进行数据交换时存在以下问题:速度不匹配:I/O设备的工作速度要比CPU慢许多,而且由于种类的不 同 , 他们之间的速度差异也很大,例如硬盘的传输速度就要比打印机快出很多 。时序不匹配:各个I/O设备都有自己的定时控制电路,以自己的速度传 输数据,无法与CPU的时序取得统一 。信息格式不匹配:不同的I/O设备存储和处理信息的格式不同 , 例如可以分为串行和并行两种;也可以分为二进制格式、ACSII编码和BCD编码等 。信息类型不匹配:不同I/O设备采用的信号类型不同,有些是数字信号,而 有些是模拟信号,因此所采用的处理方式也不同 。基于以上原因,CPU与外设之间的数据交换必须通过接口来完成,通常接口有以下一些功能:?。?)设置数据的寄存、缓冲逻辑,以适应CPU与外设之间的速度差异,接口通常由一些寄存器或RAM芯片组成,如果芯片足够大还可以实现批量数据的传输;?。?)能够进行信息格式的转换,例如串行和并行的转换;?。?)能够协调CPU和外设两者在信息的类型和电平的差异,如电平转换驱动器、数/模或模/数转换器等;?。?)协调时序差异;?。?)地址译码和设备选择功能;?。?)设置中断和DMA控制逻辑 , 以保证在中断和DMA允许的情况下产生中断和DMA请求信号,并在接受到中断和DMA应答之后完成中断处理和DMA传输 。3、接口的控制方式CPU通过接口对外设进行控制的方式有以下几种:?。?)程序查询方式这种方式下 , CPU通过I/O指令询问指定外设当前的状态,如果外设准备就绪,则进行数据的输入或输出,否则CPU等待,循环查询 。这种方式的优点是结构简单 , 只需要少量的硬件电路即可,缺点是由于CPU的速度远远高于外设,因此通常处于等待状态 , 工作效率很低?。?)中断处理方式在这种方式下,CPU不再被动等待,而是可以执行其他程序,一旦外设为数据交换准备就绪,可以向CPU提出服务请求,CPU如果响应该请求 , 便暂时停止当前程序的执行,转去执行与该请求对应的服务程序,完成后,再继续执行原来被中断的程序 。中断处理方式的优点是显而易见的,它不但为CPU省去了查询外设状态和等待外设就绪所花费的时间,提高了CPU的工作效率,还满足了外设的实时要求 。但需要为每个I/O设备分配一个中断请求号和相应的中断服务程序,此外还需要一个中断控制器(I/O接口芯片)管理I/O设备提出的中断请求,例如设置中断屏蔽、中断请求优先级等 。此外,中断处理方式的缺点是每传送一个字符都要进行中断,启动中断控制器 , 还要保留和恢复现场以便能继续原程序的执行,花费的工作量很大,这样如果需要大量数据交换,系统的性能会很低 。?。?)DMA(直接存储器存?。┐头绞?DMA最明显的一个特点是它不是用软件而是采用一个专门的控制器来控制内存与外设之间的数据交流 , 无须CPU介入,大大提高CPU的工作效率 。在进行DMA数据传送之前,DMA控制器会向CPU申请总线控制 权,CPU如果允许,则将控制权交出,因此,在数据交换时 , 总线控制权由DMA控制器掌握,在传输结束后,DMA控制器将总线控制权交还给CPU5,java io流的典型使用方式有几种Java中IO流分成两大类,一种是输入流 , 所有的输入流都直接或间接继承自InputStream抽象类,输入流作为数据的来源,我们可以通过输入流的read方法读取字节数据;另一种是输出流,所有的输出流都直接或间接继承自OutputStream抽象类,输出流接收数据 , 可以通过write方法写入字节数据 。Java的IO流类中 , 大部分的输入流和输出流都是成对存在的 , 即如果存在XXXInputStream,那么就存在XXXOutputStream,反之亦然 。SequenceInputStream和StringBufferInputStream是特例,没有对应的SequenceOutputStream类和StringBufferOutputStream类,许多IO操作都可能会抛出IOException异常,比如read、write、close操作 。以下是Java的IO流中常见的输入流,由于每个输入流都有其对应的输出流,所以此处就不再列出输出流的继承结构图 。1、ByteArrayInputStream & ByteArrayOutputStream: ByteArrayInputStream构造函数中需要传入一个byte数组作为数据源,当执行read操作时,就会从该数组中读取数据 , 正如其名 , 是一种基于字节数组实现的一种简单输入流,显而易见的是,如果在构造函数中传入了null作为字节数据,那么在执行read操作时就会出现NullPointerException异常,但是在构造函数初始化阶段不会抛出异常;与之相对应的是ByteArrayOutputStream,其内部也有一个字节数组用于存储write操作时写入的数据,在构造函数中可以传入一个size指定其内部的byte数组的大小 , 如果不指定 , 那么默认它会将byte数组初始化为32字节,当持续通过write向ByteArrayOutputStream中写入数据时 , 如果其内部的byte数组的剩余空间不能够存储需要写入的数据,那么那么它会通过调用内部的ensureCapacity方法对其内部维护的byte数组进行扩容以存储所有要写入的数据,所以不必担心其内部的byte数组太小导致的IndexOutOfBoundsException之类的异常 。2、FileInputStream & FileOutputStream FileInputStream 能够将文件作为数据源,读取文件中的流,通过File对象或文件路径等初始化,在其构造函数中,如果传入的File对象(或与其相对应的文件路径所表示的File对象)不存在或是一个目录而不是文件或者由于其他原因无法打开读取数据,都会导致在初始化阶段导致抛出FileNotFoundException异常;与FileInputStream 相对应的是FileOutputStream,可以通过FileOutputStream向文件中写入数据,也需要通过File对象或文件路径对其初始化,如同FileInputStream,如果传入的File对象(或与其相对应的文件路径所表示的File对象)是一个目录而不是文件或者由于其他原因无法创建该文件写入数据,都会导致在初始化阶段抛出FileNotFoundException异常 。3、PipedInputStream & PipedOutputStream PipedInputStream和PipedOutputStream一般是结合使用的,这两个类用于在两个线程间进行管道通信 , 一般在一个线程中执行PipedOutputStream 的write操作,而在另一个线程中执行PipedInputStream的read操作 。可以在构造函数中传入相关的流将PipedInputStream 和PipedOutputStream 绑定起来,也可以通过二者的connect方法将二者绑定起来 , 一旦二者进进行了绑定 , 那么PipedInputStream的read方法就会自动读取PipedOutputStream写入的数据 。PipedInputStream的read操作是阻塞式的,当执行PipedOutputStream的write操作时,PipedInputStream会在另一个线程中自动读取PipedOutputStream写入的内容,如果PipedOutputStream一直没有执行write操作写入数据,那么PipedInputStream的read方法会一直阻塞PipedInputStream的read方法所运行的线程直至读到数据 。单独使用PipedInputStream或单独使用PipedOutputStream时没有任何意义的,必须将二者通过connect方法(或在构造函数中传入对应的流)进行连接绑定,如果单独使用其中的某一个类,就会触发IOException: Pipe Not Connected.4、ObjectInputStream & ObjectOutputStream ObjectOutputStream具有一系列writeXXX方法,在其构造函数中可以掺入一个OutputStream,可以方便的向指定的输出流中写入基本类型数据以及String,比如writeBoolean、writeChar、writeInt、writeLong、writeFloat、writeDouble、writeCharts、writeUTF等,除此之外,ObjectOutputStream还具有writeObject方法 。writeObject方法中传入的类型必须实现了Serializable接口,从而在执行writeObject操作时将对象进行序列化成流,并将其写入指定的输出流中 。与ObjectOutputStream相对应的是ObjectInputStream,ObjectInputStream有与OutputStream中的writeXXX系列方法完全对应的readXXX系列方法,专门用于读取OutputStream通过writeXXX写入的数据 。5、SequenceInputStream SequenceInputStream 主要是将两个(或多个)InputStream在逻辑上合并为一个InputStream,比如在构造函数中传入两个InputStream,分别为in1和in2,那么SequenceInputStream在读取操作时会先读取in1,如果in1读取完毕,就会接着读取in2 。在我们理解了SequenceInputStream 的作用是将两个输入流合并为一个输入流之后,我们就能理解为什么不存在对应的SequenceOutputStream 类了,因为将一个输出流拆分为多个输出流是没有意义的 。6、StringBufferInputStream StringBufferInputStream允许通过在构造函数中传入字符串以读取字节 , 在读取时内部主要调用了String的charAt方法 。与SequenceInputStream类似 , StringBufferInputStream也没有对应的OutputStream,即不存在StringBufferOutputStream类 。Java没有设计StringBufferOutputStream类的理由也很简单,我们假设StringBufferOutputStream存在,那么StringBufferOutputStream应该是内部通过执行write操作写入数据更新其内部的String对象,比如有可能是通过StringBuilder来实现,但是这样做毫无意义,因为一旦我们String的构造函数中可以直接传入字节数组构建字符串,简单明了,所以设计StringBufferOutputStream就没有太大的必要了 。StringBufferInputStream这个类本身存在一点问题,它不能很好地将字符数组转换为字节数组 , 所以该类被Java标记为废弃的(Deprecated) , 其官方推荐使用StringReader作为代替 。7、FilterInputStream & FilterOutputStream FilterInputStream包含了其他的输入流,说具体点就是在其构造函数中需要传入一个InputStream并将其保存在其名为in的字段中 , FilterInputStream只是简单的覆盖了所有的方法,之所说是简单覆盖是因为在每个覆盖函数中 , 它只是调用内部的保存在in字段中的InputStream所对应的方法 , 比如在其覆盖read方法时,内部只是简单调用了in.read()方法 。FilterInputStream的子类可以进一步覆盖某些方法以保持接口不变的情况下实现某一特性(比如其子类有的可以通过使用缓存优化读取的效率)或者提供一些其他额外的实用方法 。所以在使用时FilterInputStream可以让传入的InputStream具有一些额外的特性 , 即对构造函数传入的InputStream进行了一层包裹,使用了典型的装饰着模式,如果只看FilterInputStream本身这一个类的话,则该类自己本身意义不大,因为其只是通过内部的字段in简单覆写某些方法 。但是如果将FilterInputStream 和其子类结合起来使用话,那么就很有用了 。比如FilterInputStream 有两个子类BufferedInputStream和DataInputStream,这两个类在下面还会详细介绍 。BufferedInputStream对read操作做了优化 , 每次读操作时都读取一大块数据,然后将其放入内部维护的一个字节数组缓冲区中 。当外面调用BufferedInputStream的read方法时 , 首先去该缓冲区中读取数据,这样就避免了频繁的实际的读操作,BufferedInputStream对外没有暴露额外的其他方法,但是其内部的read方法已经经过优化了,所以在执行读操作的时候效率更高 。DataInputStream与ObjectInputStream有点类似,可以通过一些readXXX方法读取基本类型的数据,这是非常有用的一些方法 。8、BufferedInputStream & BufferedOutputStream 如上面所介绍的那样,在BufferedInputStream的构造函数中需要传入一个InputStream, BufferedInputStream内部有一个字节数组缓冲区,每次执行read操作的时候就从这buf中读取数据 , 从buf中读取数据没有多大的开销 。如果buf中已经没有了要读取的数据 , 那么就去执行其内部绑定的InputStream的read方法,而且是一次性读取很大一块数据,以便填充满buf缓冲区 。缓冲区buf的默认大小是8192字节 , 也就是8K,在构造函数中我们也可以自己传入一个size指定缓冲区的大小 。由于我们在执行BufferedInputStream的read操作的时候,很多时候都是从缓冲区中读取的数据 , 这样就大大减少了实际执行其指定的InputStream的read操作的次数,也就提高了读取的效率 。与BufferedInputStream 相对的是BufferedOutputStream 。在BufferedOutputStream的构造函数中我们需要传入一个OutputStream,这样就将BufferedOutputStream与该OutputStream绑定在了一起 。BufferedOutputStream内部有一个字节缓冲区buf , 在执行write操作时,将要写入的数据先一起缓存在一起 , 将其存入字节缓冲区buf中,buf是有限定大小的,默认的大小是8192字节,即8KB , 当然也可以在构造函数中传入size指定buf的大小 。该buf只要被指定了大小之后就不会自动扩容,所以其是有限定大小的,既然有限定大小,就会有被填充完的时刻,当buf被填充完毕的时候会调用BufferedOutputStream的flushBuffer方法,该方法会通过调用其绑定的OutputStream的write方法将buf中的数据进行实际的写入操作并将buf的指向归零(可以看做是将buf中的数据清空) 。如果想让缓存区buf中的数据理解真的被写入OutputStream中,可以调用flush方法,flush方法内部会调用flushBuffer方法 。由于buf的存在 , 会大大减少实际执行OutputStream的write操作的次数,优化了写的效率 。4种 。。。。http://www.2cto.com/kf/201312/262036.html

    推荐阅读