计算机系统应用教程网站

网站首页 > 技术文章 正文

你真的了解同步/异步 阻塞/非阻塞吗?

btikc 2024-10-21 04:09:45 技术文章 14 ℃ 0 评论

主体

同步/异步:针对的主体是客户端。

阻塞/非阻塞:针对的主体是服务端。

概述

同步:客户端发出请求等待返回数据后才会进行下一步操作;应用程序在数据未返回期间处于阻塞状态(类似于僵死)。

异步:客户端请求发出后,不用等待返回结果,即可执行下一步操作;当数据返回时,通过状态、通知或回调获取数据。

阻塞:服务器调用函数时在结果返回之前,当前线程会被阻塞挂起;函数只有在得到结果之后才会返回。

非阻塞:服务器调用函数时 若此函数的结果不能立刻返回(比如IO操作),该函数不会被阻塞挂起而是立刻返回(当然此时返回的结果不会是我们需要的 所以要做额外的处理)。

单看这些概述是不是觉得还不错呢,感觉可以分清楚了呢!然而日常面试或者使用中更多则谈及的是他们组合使用。


这里要谈一个很重要的点:客户端计算机处理请求调用的时候在内核有两个操作会阻塞应用程序的运行,第一个是等待数据的过程(IO或硬盘数据的读取等),第二个是把数据从内核空间拷贝到用户空间的过程;以上两步操作哪怕只有一丁点的阻塞那么这个处理都是同步的 即客户端会有僵死状态的出现,哪怕这个僵死的时间只有0.01秒。异步请求对于以上两步的操作是全程无阻塞的都会由系统操作完毕后再进行通知回调,即客户端不会有一丝一毫的僵死,所以异步的阻塞与非阻塞的组合对于客户端的体验以及性能影响不大,故很少谈及他们。所以下面我也将只针对同步阻塞同步非阻塞与异步非阻塞组合展开介绍。

同步阻塞

用户空间的应用程序发起调用,这会导致应用程序阻塞。这意味着应用程序会一直阻塞,直到调用完成为止(数据传输完成或发生错误)。阻塞线程会被挂起应用程序处于一种不再消费 CPU 而只是简单等待响应的状态。

同步非阻塞

非阻塞的实现是发起的调用可能并不会立即满足,需要应用程序调用许多次来等待操作完成。这可能效率不高,因为在很多情况下,当内核执行这个命令时,应用程序必须要进行忙碌等待,直到数据可用为止。对于同步非阻塞的实现除了轮询之外还有我们平时所说的多路IO复用及信号驱动,因为不管是哪一种策略都会在第二步被阻塞。

异步非阻塞

异步虽好,但编程的复杂度相比于同步可不是一个维度的存在。


本猿是一名自学而成的JAVA程序猿,仅此记录个猿的学习过程及理解,无误导他猿之嫌。

对于知识的理解可能会有偏颇,以上内容也仅仅是我的个猿的总结观点,如有错误纰漏还请不吝赐教,我会及时改正。


“知行合一是我将为之追求一生的信条”

本文暂时没有评论,来添加一个吧(●'◡'●)

欢迎 发表评论:

最近发表
标签列表