搞不清楚同步,阻塞,异步,非阻塞这些概念

2013-04-06 09:51:35 +08:00
 pythonee
同步,阻塞,异步,非阻塞,这几个概念实在是容易把人搞乱,查了很多资料,发现线程中的阻塞/非阻塞和IO中的概念还有点不一样,这又让人更加混乱了。

现在,我只想搞清楚这几个概念在IO中的含义与实例,在理解这些概念的时候,没有实例,实在是有点难弄清楚。另外,java中的nio到底是异步非阻塞还是同步非阻塞啊,我见到了两种说法。我想,弄清楚上面那些概念后,这个答案也自然出来了。

另外,有没有同步非阻塞或异步阻塞模型的实际用例啊
9551 次点击
所在节点    编程
30 条回复
sillyousu
2013-04-10 21:12:54 +08:00
@pythonee

我想应该是的。不过我不会 java 囧
pythonee
2013-04-10 21:55:29 +08:00
@sillyousu

呵呵,那我只好去跟下代码了,这个是个大坑我觉得
G_will
2013-04-30 22:56:19 +08:00
看了回帖觉得有必要插一腿:

1. 举例子说这个问题很不好,越说越混乱,因为:a. 比喻只能给我们描述本体和喻体大致的相似,而正是那些细微的差别才是理解这个问题的关键 b. 所有现实中的例子都和计算机世界中有一个本质的差别就是现实中复制物体成本很大,计算机中复制就复制了。 回题,我们说的是计算机的描述 IO 的模型,那我们就以此说好了。

2. 阻塞对应着非阻塞,但同步不对应着异步,异步的更多的意思是会有异步的情况发生但是也有可能是同步的。

3. 阻塞非阻塞、异步同步,这两组概念并非正交,所以这两组词组合出的四种 IO 类型也不是完全的没有交集。

4. 我们在说 IO 模型,指的是一种 IO 情景表现出的情形,我们可以说这个代码是属于某某 IO 模型,但不能说某某 IO 模型一定就是怎么怎么实现的。所以,当我们讨论不同范畴的代码逻辑时,IO 模型是有可能不同的,也许整体程序上是阻塞的,但是其中一个接口请求是非阻塞的。所以,很多讨论 select 和 epoll 是什么模型的时候就会陷入混乱,因为大家说的范畴不一样。
G_will
2013-04-30 23:12:51 +08:00
另外补一个同步非阻塞的实际用例, agentzh 老师领导的 OpenResty 项目中 ngx_lua 通常就是同步非阻塞的 IO 模型,当有 IO 任务时,主动将 IO 切分为更小的逻辑,并且 yield 控制权,所以当 IO 发生时,整个程序的执行顺序与编写预期顺序是一致的,同步,因为只进行一点 IO 就 yield 出进行处理,所以没有没有阻塞整个程序,是非阻塞。
zava
2013-05-02 14:09:24 +08:00
@pythonee 可以参考一下我之前的博客, 关于IO的同步,异步,阻塞,非阻塞:http://www.zavakid.com/2011/07/30/unix-io-model/
luoqeng
2013-05-03 12:30:05 +08:00
同步和异步是指一个过程而言,同步:过程是按照固定次序执行的,前后次需是有明确逻辑语义的,不能颠倒。而异步,则对次序要求不严格。也就是说作为过程执行主体(如应用程序)在执行过程中是否等待 服务方的返回,等待则是同步,否则是异步。只有等待返回后才继续进行后续步骤。

阻塞非阻塞:是指某执行函数、过程是否立刻返回。也就是程序调用某个函数是否立刻返回。在程序中,程序是由无数个函数、小过程体组成的,往往这些一般是系统预定义的。

同步异步是站在程序的视角看的,同步是有次序不可随意划分颠倒的,异步次序不是固定的。
阻塞非阻塞是指组成程序的各个单位、元素而言,粒度不同。这些单位组成了一个程序体。比如系统函数,当然也有自定义函数

http://blog.chinaunix.net/uid-52437-id-2108895.html
miaoever
2013-05-03 12:37:48 +08:00
毛遂自荐一篇自己的拙作,希望能有帮助
http://miaoo.in/talk-about-unix-io-model.html
barb
2013-05-03 13:46:10 +08:00
I/O 同异步方面的认识,的确是大师级程序员要搞明白的事
est
2013-05-03 14:22:40 +08:00
就拿去去银行办理业务,排队来说:

blocking:人少直接办理业务;如果人多,就排队等待,再办理业务。
non-block:人多需要排队 -> 办理业务失败 -> 直接放弃;人少 -> 运气好就直接办理下来了。

sync:取号之后就呆呆等着一直轮到我开始办理业务。一次只做一件事。按顺序做事。
async:取号之后,我去做点其他事情,轮到我了再办理业务。先后顺序不用管了。

其中async的信号(或者说回调)也有两种模式,一种是轮到我了,反复喊号,一直到催促成功。另一种是一次喊号失败了就不管了。爱来不来。

顺便介绍一下Unix下几种模式吧:

复用(multiplexing):手里有多个业务需要办理。一次性观察多个窗口排队情况,哪个人少去哪个。

SIGIO:把所有窗口流水号处理情况搜集起来,筛选出自己需要的窗口是否有空。有空就去办,否则继续看流水
JackyHua
2013-05-04 15:23:47 +08:00
不错学习了

这是一个专为移动设备优化的页面(即为了让你能够在 Google 搜索结果里秒开这个页面),如果你希望参与 V2EX 社区的讨论,你可以继续到 V2EX 上打开本讨论主题的完整版本。

https://www.v2ex.com/t/65058

V2EX 是创意工作者们的社区,是一个分享自己正在做的有趣事物、交流想法,可以遇见新朋友甚至新机会的地方。

V2EX is a community of developers, designers and creative people.

© 2021 V2EX