node中异步IO的理解
解释性语言和编译型语言的区别:
计算器不能直接的理解高级语言,只能理解机器语言,所以必须把高级语言翻译为机器语言,翻译的方式有两种,一个是编译,一个是解释。
解释性语言的程序不需要编译,它是在运行程序的时候进行翻译,比如java,专门有一个解释器可以直接执行Java程序,每一个语句都是执行的时候才能翻译,编译型就是编译的时候直接编译成机器可以执行的,编译和执行时分开的,但是不能跨平台。因为翻译只做了一次,运行的时候不需要再去翻译,所以编译型语言的程序执行效率高。
对于解释性语言,程序运行时的控制权在解释器而不在于程序,对于编译型语言程序运行时的控制权在程序。
进程的前台运行和后台运行
后台进程是一直运行的服务端程序,又称为守护进程,通常是在系统后台运行,没有控制终端,不与前台交互,一般作为系统服务使用。其称为后台进程的原因大部分是因为它没有控制端,无法和前台的用户交互。
相对应的前台进程,就是我们在终端中开启的进程,例如我们在终端中npm run server.js启动一个webServer,此时启动的进程就是前台进程,当你把当前的命令行终端进行关闭了之后,该进程也便被杀死了。
node中的阻塞/非阻塞IO和同步/异步IO
表面上来看,这两组的概念都差不多,阻塞/非阻塞IO,是操作系统内核对于IO的两种处理方式,对于阻塞IO,比如读取文件,操作系统在读取完文件之后,才会给应用程序返回结果,这一段过程呢,应用程序在等待操作系统的回复,是为应用层面的同步IO。
对于非阻塞IO,操作系统在接收到应用程序对于读取文件的请求时,立即返回给应用程序一个结果,但是应用程序怎么知道操作系统完成了IO操作呢?这时候应用程序就会对操作系统发起询问(你到底好了没有?人家都快急死了),发起询问的方法又经过好几种演变,比如read、poll、epoll等,中间多的无非就是根据文件描述符减少询问的次数,总体上来说这种方式不好。并不能达到我们理想的异步IO。
那么从应用程序方面来将,我们期望的异步IO,就是应用程序进行了IO操作之后,不再需要操心操作系统什么时候返回,去执行下边的代码就行了,当操作执行完了之后呢,直接给应用程序发信息告诉他就行了。Linux系统下原生提供了一种AIO是通过信号或者回调来传递数据的,这个AIO就是我们的理想的异步IO。但是不幸的是只有Linux中有,而且无法利用系统缓存。
node(单线程)中对于*nix平台而言,采用的是线程池+epoll异步IO模拟实现应用程序层面的异步IO,主线程进行执行程序,碰到我们异步IO调用时,将改异步IO分配给线程池中的某一个线程,然后就变成了线程池中的某个线程和操作系统的阻塞IO进行IO操作,当IO线程接收到操作系统的阻塞IO执行的返回结果之后,IO线程再发送时间给主线程。
node中对于window平台而言,是依靠于IOCP来实现的,其内部仍然是线程池原理,不同之处在于这些线程池由系统内核接手管理。
node中对于异步IO的实现:
对于异步IO的实现,其中有几个组成部分:事件循环、观察者、请求对象
事件循环是node中的一种执行机制,这种机制是回调执行的基础部分,它保证了我们的回调函数能够被执行。
观察者是暴露回调函数的窗口,如果整体的场景为饮料工厂的话,我们的瓶子就是我们的回调函数,事件循环就是传送带在那一直转,而观察者就是瓶子就如机器的入口,机器就是我们的应用程序。所以应用程序从观察者这里获取事件,应用程序询问观察者是否还有事件。
请求对象,是应用程序封装的一个对象,里边包含了要做的IO操作类型,以及回调函数。
整体流程就是,异步调用开始之后,应用程序封装一个请求对象,送入我们的线程池中的某个线程,该线程和操作系统的非阻塞IO通过epoll机制进行工作,这其中,会有观察者在线程池中进行检查,当某个线程的IO操作完成之后,观察者会将回调函数(封装在请求对象中的)放在事件循环上(上段提到的传送带),然后主线程调用回调函数。
参考:《深入浅出Node.js》
问题思考:
- 操作系统的线程与CPU中的线程有什么不同?
node中异步IO的理解的更多相关文章
- Java网络编程中异步编程的理解
目录 前言 一.异步,同步,阻塞和非阻塞的理解 二.异步编程从用户层面和框架层面不同角度的理解 用户角度的理解 框架角度的理解 三.为什么使用异步 四.理解这些能在实际中的应用 六.困惑 参考文章 前 ...
- Node.js异步IO原理剖析
为什么要异步I/O? 从用户体验角度讲,异步IO可以消除UI阻塞,快速响应资源 JavaScript是单线程的,它与UI渲染共用一个线程.所以在JavaScript执行的时候,UI渲染将处于停顿的状态 ...
- 小白对异步IO的理解
前言 看到越来越多的大佬都在使用python的异步IO,协程等概念来实现高效的IO处理过程,可是我对这些概念还不太懂,就学习了一下. 因为是初学者,在理解上有很多不到位的地方,如果有错误,还希望能够有 ...
- python IO模式(多路复用和异步IO深入理解)
1.事件渠道模型.事件渠道为异步IO的原型. 2.IO模式,一次IO调用会经历两个阶段.一.等待数据阶段,将数据从网络或者是磁盘读取到系统内核(kennel) 二.将数据从内核拷贝到进程中. 基于这两 ...
- 同步IO, 异步IO的理解
1. 什么是IO? 在计算机中无时无刻不存在着对数据的访问和读取(数据都存储在物理的媒介上,例如寄存器,高速缓存,内存,磁盘,网卡等等),这些操作被称为IO. 2. 阻塞IO (1)当用户线程发起IO ...
- 深入理解node.js异步编程:基础篇
###[本文是基础内容,大神请绕道,才疏学浅,难免纰漏,请各位轻喷] ##1. 概述 目前开源社区最火热的技术当属Node.js莫属了,作为使用Javascript为主要开发语言的服务器端编程技术和平 ...
- [译]Python中的异步IO:一个完整的演练
原文:Async IO in Python: A Complete Walkthrough 原文作者: Brad Solomon 原文发布时间:2019年1月16日 翻译:Tacey Wong 翻译时 ...
- 异步IO比同步阻塞IO性能更好吗?为什么?
最近在看node.js, 介绍中提到node是异步io的方式实现, 性能比同步阻塞io的更好. 对于一个request而言, 如果我们依赖io的结果, 异步io和同步阻塞io都是要等到io完成才能继续 ...
- 深入浅出node(4) 异步编程
一)函数式编程基础 二)异步编程的优势和难点 2.1 优势 2.2 难点 2.2.1 异常处理 2.2.2 函数嵌套过深 2.2.3 阻塞 2.2.4 多线程编程 2.2.5 异步转同步 三)异步编程 ...
随机推荐
- Django_rest_framework_版本(待验证)
简介 API版本控制可以用来在不同的客户端使用不同的行为.REST框架提供了大量不同的版本设计. 版本控制是由传入的客户端请求决定的,并且可能基于请求URL,或者基于请求头. 有许多有效的方法达到版本 ...
- jsp九大内置对象之config 和 out
jsp中config的作用是读取web.xml中的配置信息,一般在后台获取初始化的参数,jsp页面用的较少因为jsp属于表现层,一般是获取数据. jsp中的out对象是将内容放到缓冲区中然后显示出来
- Python中,os.listdir遍历纯数字文件乱序如何解决
Python中,os.listdir遍历纯数字文件乱序如何解决 日常跑深度学习视觉相关代码时,常常需要对数据集进行处理.许多图像文件名是利用纯数字递增的方式命名.通常所用的排序函数sort(),是按照 ...
- golang string转json的一些坑
先带来点冷知识,不知道大家知不知道,反正我刚知道... 大佬们都知道怎么在string中给string类型赋值带双引号的字符串,没错就是用反斜杠,如下: msg := "{\"na ...
- 深入理解Java类加载器(2)
1 基本信息 每个开发人员对Java.lang.ClassNotFoundExcetpion这个异常肯定都不陌生,这背后就涉及到了java技术体系中的类加载.Java的类加载机制是技术体系中比较核心的 ...
- 解决Shiro+SpringBoot自定义Filter不生效问题
在SpringBoot+Shiro实现安全框架的时候,自定义扩展了一些Filter,并注册到ShiroFilter,但是运行的时候发现总是在ShiroFilter之前就进入了自定义Filter,结果当 ...
- 关于VS2005中C#代码用F12转到定义时,总是显示从元数据的问题
元数据是:NET 程序集中的标记信息. 是在代码中选择了转到定义时候给定位的吧.因为没有找到源代码,VS通过反射读取元数据中的信息生成了那个. 解决方法: 1. 要把项目先添加到解决方案中. 2. 再 ...
- 如何获取app的activity
(一) 本机安装appium的环境后,在cmd中输入:adb logcat>D:/log.log (二)真题连接电脑或在虚拟机中启动被测试app (三)直接查看d盘的log.log即可从来里面找 ...
- Excelutil 工具类
1.说明:ExcelUtil主要用于获得单元格的数据和对对指定单元格中写入数据用! 相关代码如下: package main.java; import java.io.File; import jav ...
- 动态生成lookup字段
var i: Integer;begin //ADOQuery已打开 //在数据集打开的情况下新增加一个字段 with Self.ADOQuery1 do begin TDataSe ...