『?jiǎn)巍痪€程能實(shí)現(xiàn)『并發(fā)』嗎?
多線程可以實(shí)現(xiàn)并發(fā)是毋庸置疑的,但是單線程是否能實(shí)現(xiàn)并發(fā)呢?
這就像我們知道多個(gè)人肯定可以同時(shí)做多件事,然后有人問(wèn)一個(gè)人可以同時(shí)做多件事嗎?答案當(dāng)然也是可以。比如很多人就經(jīng)常邊吃飯邊玩手機(jī),在工作中一個(gè)人也經(jīng)常被上級(jí)同時(shí)安排大大小小多個(gè)任務(wù)。線程也是同理,所以單線程可以實(shí)現(xiàn)并發(fā)。
看到有人在也是回答“能”的情況下,說(shuō)單線程實(shí)現(xiàn)的并發(fā)是“偽并發(fā)”,個(gè)人覺(jué)得這種說(shuō)法是有問(wèn)題的。并發(fā)就是并發(fā),并不存在所謂“偽并發(fā)”。我大概也能猜到提出“偽并發(fā)”概念的人的意思,他認(rèn)為的“真并發(fā)”其實(shí)是“并行”,其認(rèn)為無(wú)法實(shí)現(xiàn)并行的并發(fā)就是“偽并發(fā)”。
但是,在弄清楚“并發(fā)”和“并行”兩個(gè)概念后,就會(huì)發(fā)現(xiàn)所謂“偽并發(fā)”是個(gè)多余、甚至?xí)又卣`解的概念。并發(fā)說(shuō)的是可以同時(shí)進(jìn)行多個(gè)任務(wù),但是它并不承諾這多個(gè)任務(wù)是“絕對(duì)的同時(shí)”開(kāi)始,也不承諾多個(gè)任務(wù)是“絕對(duì)的同時(shí)”進(jìn)行,而實(shí)現(xiàn)了后兩者的情況則被稱(chēng)為“并行”。
即并發(fā)不一定并行,但是并行一定是并發(fā)。
在談?wù)摬l(fā)時(shí)所說(shuō)的“同時(shí)”的“時(shí)”是個(gè)相對(duì)的、可變的“時(shí)間刻度”。兩件事是否算并發(fā),隨著這個(gè)“時(shí)間刻度”的變化也會(huì)發(fā)生變化。比如前文說(shuō)很多人經(jīng)常邊吃飯邊玩手機(jī)是并發(fā),較真的人可能就會(huì)不同意,覺(jué)得兩件事明明只能先后進(jìn)行,原因就在于我和他在談?wù)摬l(fā)時(shí)的“時(shí)間刻度”沒(méi)統(tǒng)一。
假設(shè)某人吃飯大概10分鐘時(shí)間,于是將10分鐘視為一個(gè)不可分割的時(shí)間單位,如果在這個(gè)時(shí)間單位內(nèi)還可以做其他事,就是實(shí)現(xiàn)了并發(fā)。但另一個(gè)人覺(jué)得并發(fā)的“時(shí)間刻度”最多為1秒,而1秒時(shí)間內(nèi)顯然不能邊吃飯邊做其他事,于是他認(rèn)為并發(fā)不成立。其實(shí)兩種說(shuō)法都沒(méi)問(wèn)題,只是并發(fā)的尺度不同。
并發(fā)是個(gè)應(yīng)用場(chǎng)景遠(yuǎn)大于并行,且在具體表現(xiàn)上可以非常靈活的執(zhí)行機(jī)制。比如計(jì)算機(jī)領(lǐng)域的單核處理器可以做多并發(fā),一個(gè)人做事也可以是多并發(fā),工廠里如同隊(duì)列執(zhí)行的單條流水線,其本質(zhì)也是大并發(fā)。相比于并行,并發(fā)在理論上更先進(jìn),在實(shí)現(xiàn)上卻更簡(jiǎn)單。
對(duì)并發(fā)的靈活應(yīng)用,讓福特汽車(chē)在1913年就架設(shè)了自己的生產(chǎn)流水線,然后將汽車(chē)裝配速度一下子提高了8倍,創(chuàng)造了駭人的每10秒就有一臺(tái)T型車(chē)下線的記錄。
重新回到計(jì)算機(jī)技術(shù)上來(lái),我們知道JavaScript是典型的單線程腳本語(yǔ)言,可是基于JavaScript的NodeJS的最大優(yōu)勢(shì)之一卻是“超強(qiáng)的高并發(fā)能力”。
也就是單線程不但可以實(shí)現(xiàn)并發(fā),在實(shí)際應(yīng)用中還是被用來(lái)實(shí)現(xiàn)“高并發(fā)”的利器,因?yàn)樗梢酝瑫r(shí)結(jié)合單線程對(duì)服務(wù)器資源的低要求和“異步”任務(wù)互不影響導(dǎo)致的事實(shí)上的“并發(fā)”這兩個(gè)優(yōu)勢(shì)。