<kbd id="afajh"><form id="afajh"></form></kbd>
<strong id="afajh"><dl id="afajh"></dl></strong>
    <del id="afajh"><form id="afajh"></form></del>
        1. <th id="afajh"><progress id="afajh"></progress></th>
          <b id="afajh"><abbr id="afajh"></abbr></b>
          <th id="afajh"><progress id="afajh"></progress></th>

          面試官:?jiǎn)魏?CPU 支持 Java 多線程嗎?為什么?被問(wèn)懵了!

          共 3061字,需瀏覽 7分鐘

           ·

          2022-11-08 21:04

          關(guān)注我們,設(shè)為星標(biāo),每天7:40不見(jiàn)不散,架構(gòu)路上與您共享

          回復(fù)架構(gòu)師獲取資源


          大家好,我是你們的朋友架構(gòu)君,一個(gè)會(huì)寫(xiě)代碼吟詩(shī)的架構(gòu)師。

          'javajgs.com';


          原文:
          blog.csdn.net/alex_xfboy/article/details/90722654


          由于現(xiàn)在大多計(jì)算機(jī)都是多核CPU,多線程往往會(huì)比單線程更快,更能夠提高并發(fā),但提高并發(fā)并不意味著啟動(dòng)更多的線程來(lái)執(zhí)行。更多的線程意味著線程創(chuàng)建銷(xiāo)毀開(kāi)銷(xiāo)加大、上下文非常頻繁,你的程序反而不能支持更高的TPS。

          時(shí)間片

          多任務(wù)系統(tǒng)往往需要同時(shí)執(zhí)行多道作業(yè)。作業(yè)數(shù)往往大于機(jī)器的CPU數(shù),然而一顆CPU同時(shí)只能執(zhí)行一項(xiàng)任務(wù),如何讓用戶(hù)感覺(jué)這些任務(wù)正在同時(shí)進(jìn)行呢? 操作系統(tǒng)的設(shè)計(jì)者 巧妙地利用了時(shí)間片輪轉(zhuǎn)的方式

          時(shí)間片是CPU分配給各個(gè)任務(wù)(線程)的時(shí)間!

          思考:?jiǎn)魏薈PU為何也支持多線程呢?

          線程上下文是指某一時(shí)間點(diǎn) CPU 寄存器和程序計(jì)數(shù)器的內(nèi)容,CPU通過(guò)時(shí)間片分配算法來(lái)循環(huán)執(zhí)行任務(wù)(線程),因?yàn)闀r(shí)間片非常短,所以CPU通過(guò)不停地切換線程執(zhí)行。

          換言之,單CPU這么頻繁,多核CPU一定程度上可以減少上下文切換。

          超線程

          現(xiàn)代CPU除了處理器核心之外還包括寄存器、L1L2緩存這些存儲(chǔ)設(shè)備、浮點(diǎn)運(yùn)算單元、整數(shù)運(yùn)算單元等一些輔助運(yùn)算設(shè)備以及內(nèi)部總線等。一個(gè)多核的CPU也就是一個(gè)CPU上有多個(gè)處理器核心,就意味著程序的不同線程需要經(jīng)常在CPU之間的外部總線上通信,同時(shí)還要處理不同CPU之間不同緩存導(dǎo)致數(shù)據(jù)不一致的問(wèn)題。

          超線程這個(gè)概念是Intel提出的,簡(jiǎn)單來(lái)說(shuō)是在一個(gè)CPU上真正的并發(fā)兩個(gè)線程,由于CPU都是分時(shí)的(如果兩個(gè)線程A和B,A正在使用處理器核心,B正在使用緩存或者其他設(shè)備,那AB兩個(gè)線程就可以并發(fā)執(zhí)行,但是如果AB都在訪問(wèn)同一個(gè)設(shè)備,那就只能等前一個(gè)線程執(zhí)行完后一個(gè)線程才能執(zhí)行)。實(shí)現(xiàn)這種并發(fā)的原理是 在CPU里加了一個(gè)協(xié)調(diào)輔助核心,根據(jù)Intel提供的數(shù)據(jù),這樣一個(gè)設(shè)備會(huì)使得設(shè)備面積增大5%,但是性能提高15%~30%。

          上下文切換

          • 線程切換,同一進(jìn)程中的兩個(gè)線程之間的切換
          • 進(jìn)程切換,兩個(gè)進(jìn)程之間的切換
          • 模式切換,在給定線程中,用戶(hù)模式和內(nèi)核模式的切換
          • 地址空間切換,將虛擬內(nèi)存切換到物理內(nèi)存

          CPU切換前把當(dāng)前任務(wù)的狀態(tài)保存下來(lái),以便下次切換回這個(gè)任務(wù)時(shí)可以再次加載這個(gè)任務(wù)的狀態(tài),然后加載下一任務(wù)的狀態(tài)并執(zhí)行。任務(wù)的狀態(tài)保存及再加載, 這段過(guò)程就叫做上下文切換。

          每個(gè)線程都有一個(gè)程序計(jì)數(shù)器(記錄要執(zhí)行的下一條指令),一組寄存器(保存當(dāng)前線程的工作變量),堆棧(記錄執(zhí)行歷史,其中每一幀保存了一個(gè)已經(jīng)調(diào)用但未返回的過(guò)程)。

          寄存器 是 CPU 內(nèi)部的數(shù)量較少但是速度很快的內(nèi)存(與之對(duì)應(yīng)的是 CPU 外部相對(duì)較慢的 RAM 主內(nèi)存)。寄存器通過(guò)對(duì)常用值(通常是運(yùn)算的中間值)的快速訪問(wèn)來(lái)提高計(jì)算機(jī)程序運(yùn)行的速度。

          程序計(jì)數(shù)器是一個(gè)專(zhuān)用的寄存器,用于表明指令序列中 CPU 正在執(zhí)行的位置,存的值為正在執(zhí)行的指令的位置或者下一個(gè)將要被執(zhí)行的指令的位置。

          • 掛起當(dāng)前任務(wù)(線程/進(jìn)程),將這個(gè)任務(wù)在 CPU 中的狀態(tài)(上下文)存儲(chǔ)于內(nèi)存中的某處
          • 恢復(fù)一個(gè)任務(wù)(線程/進(jìn)程),在內(nèi)存中檢索下一個(gè)任務(wù)的上下文并將其在 CPU 的寄存器中恢復(fù)
          • 跳轉(zhuǎn)到程序計(jì)數(shù)器所指向的位置(即跳轉(zhuǎn)到任務(wù)被中斷時(shí)的代碼行),以恢復(fù)該進(jìn)程在程序中

          線程上下文切換會(huì)有什么問(wèn)題呢?

          上下文切換會(huì)導(dǎo)致額外的開(kāi)銷(xiāo),常常表現(xiàn)為高并發(fā)執(zhí)行時(shí)速度會(huì)慢串行,因此減少上下文切換次數(shù)便可以提高多線程程序的運(yùn)行效率。

          • 直接消耗:指的是CPU寄存器需要保存和加載, 系統(tǒng)調(diào)度器的代碼需要執(zhí)行, TLB實(shí)例需要重新加載, CPU 的pipeline需要刷掉
          • 間接消耗:指的是多核的cache之間得共享數(shù)據(jù), 間接消耗對(duì)于程序的影響要看線程工作區(qū)操作數(shù)據(jù)的大小

          切換查看

          Linux系統(tǒng)下可以使用vmstat命令來(lái)查看上下文切換的次數(shù), 其中cs列就是指上下文切換的數(shù)目(一般情況下, 空閑系統(tǒng)的上下文切換每秒大概在1500以下)

          線程調(diào)度

          搶占式調(diào)度

          指的是每條線程執(zhí)行的時(shí)間、線程的切換都由系統(tǒng)控制,系統(tǒng)控制指的是在系統(tǒng)某種運(yùn)行機(jī)制下,可能每條線程都分同樣的執(zhí)行時(shí)間片,也可能是某些線程執(zhí)行的時(shí)間片較長(zhǎng),甚至某些線程得不到執(zhí)行的時(shí)間片。在這種機(jī)制下,一個(gè)線程的堵塞不會(huì)導(dǎo)致整個(gè)進(jìn)程堵塞。

          java使用的線程調(diào)使用搶占式調(diào)度,Java中線程會(huì)按優(yōu)先級(jí)分配CPU時(shí)間片運(yùn)行,且優(yōu)先級(jí)越高越優(yōu)先執(zhí)行,但優(yōu)先級(jí)高并不代表能獨(dú)自占用執(zhí)行時(shí)間片,可能是優(yōu)先級(jí)高得到越多的執(zhí)行時(shí)間片,反之,優(yōu)先級(jí)低的分到的執(zhí)行時(shí)間少但不會(huì)分配不到執(zhí)行時(shí)間。

          協(xié)同式調(diào)度

          指某一線程執(zhí)行完后主動(dòng)通知系統(tǒng)切換到另一線程上執(zhí)行,這種模式就像接力賽一樣,一個(gè)人跑完自己的路程就把接力棒交接給下一個(gè)人,下個(gè)人繼續(xù)往下跑。線程的執(zhí)行時(shí)間由線程本身控制,線程切換可以預(yù)知,不存在多線程同步問(wèn)題,但它有一個(gè)致命弱點(diǎn):如果一個(gè)線程編寫(xiě)有問(wèn)題,運(yùn)行到一半就一直堵塞,那么可能導(dǎo)致整個(gè)系統(tǒng)崩潰。

          線程讓出cpu的情況
          • 當(dāng)前運(yùn)行線程主動(dòng)放棄CPU,JVM暫時(shí)放棄CPU操作(基于時(shí)間片輪轉(zhuǎn)調(diào)度的JVM操作系統(tǒng)不會(huì)讓線程永久放棄CPU,或者說(shuō)放棄本次時(shí)間片的執(zhí)行權(quán)),例如調(diào)用yield()方法。
          • 當(dāng)前運(yùn)行線程因?yàn)槟承┰蜻M(jìn)入阻塞狀態(tài),例如阻塞在I/O上
          • 當(dāng)前運(yùn)行線程結(jié)束,即運(yùn)行完run()方法里面的任務(wù)

          引起線程上下文切換的因素

          • 當(dāng)前執(zhí)行任務(wù)(線程)的時(shí)間片用完之后,系統(tǒng)CPU正常調(diào)度下一個(gè)任務(wù)
          • 中斷處理,在中斷處理中,其他程序”打斷”了當(dāng)前正在運(yùn)行的程序。當(dāng)CPU接收到中斷請(qǐng)求時(shí),會(huì)在正在運(yùn)行的程序和發(fā)起中斷請(qǐng)求的程序之間進(jìn)行一次上下文切換。中斷分為硬件中斷和軟件中斷,軟件中斷包括因?yàn)镮O阻塞、未搶到資源或者用戶(hù)代碼等原因,線程被掛起。
          • 用戶(hù)態(tài)切換,對(duì)于一些操作系統(tǒng),當(dāng)進(jìn)行用戶(hù)態(tài)切換時(shí)也會(huì)進(jìn)行一次上下文切換,雖然這不是必須的。
          • 多個(gè)任務(wù)搶占鎖資源,在多任務(wù)處理中,CPU會(huì)在不同程序之間來(lái)回切換,每個(gè)程序都有相應(yīng)的處理時(shí)間片,CPU在兩個(gè)時(shí)間片的間隔中進(jìn)行上下文切換


          因此優(yōu)化手段有:
          • 無(wú)鎖并發(fā)編程,多線程處理數(shù)據(jù)時(shí),可以用一些辦法來(lái)避免使用鎖,如將數(shù)據(jù)的ID按照Hash取模分段,不同的線程處理不同段的數(shù)據(jù)
          • CAS算法,Java的Atomic包使用CAS算法來(lái)更新數(shù)據(jù),而不需要加鎖
          • 使用最少線程
          • 協(xié)程,單線程里實(shí)現(xiàn)多任務(wù)的調(diào)度,并在單線程里維持多個(gè)任務(wù)間的切換

          合理設(shè)置線程數(shù)目既可以最大化利用CPU,又可以減少線程切換的開(kāi)銷(xiāo)。

          • 高并發(fā),低耗時(shí)的情況,建議少線程。
          • 低并發(fā),高耗時(shí)的情況:建議多線程。
          • 高并發(fā)高耗時(shí),要分析任務(wù)類(lèi)型、增加排隊(duì)、加大線程數(shù)


          到此文章就結(jié)束了。Java架構(gòu)師必看一個(gè)集公眾號(hào)、小程序、網(wǎng)站(3合1的文章平臺(tái),給您架構(gòu)路上一臂之力,javajgs.com)。如果今天的文章對(duì)你在進(jìn)階架構(gòu)師的路上有新的啟發(fā)和進(jìn)步,歡迎轉(zhuǎn)發(fā)給更多人。歡迎加入架構(gòu)師社區(qū)技術(shù)交流群,眾多大咖帶你進(jìn)階架構(gòu)師,在后臺(tái)回復(fù)“加群”即可入群。

          第23期已結(jié)束!第24期已開(kāi)始,11月1號(hào)截止



          這些年小編給你分享過(guò)的干貨


          1.idea永久激活碼(親測(cè)可用)

          2.優(yōu)質(zhì)ERP系統(tǒng)帶進(jìn)銷(xiāo)存財(cái)務(wù)生產(chǎn)功能(附源碼)

          3.優(yōu)質(zhì)SpringBoot帶工作流管理項(xiàng)目(附源碼)

          4.最好用的OA系統(tǒng),拿來(lái)即用(附源碼)

          5.SBoot+Vue外賣(mài)系統(tǒng)前后端都有(附源碼

          6.SBoot+Vue可視化大屏拖拽項(xiàng)目(附源碼)


          轉(zhuǎn)發(fā)在看就是最大的支持??

          瀏覽 58
          點(diǎn)贊
          評(píng)論
          收藏
          分享

          手機(jī)掃一掃分享

          分享
          舉報(bào)
          評(píng)論
          圖片
          表情
          推薦
          點(diǎn)贊
          評(píng)論
          收藏
          分享

          手機(jī)掃一掃分享

          分享
          舉報(bào)
          <kbd id="afajh"><form id="afajh"></form></kbd>
          <strong id="afajh"><dl id="afajh"></dl></strong>
            <del id="afajh"><form id="afajh"></form></del>
                1. <th id="afajh"><progress id="afajh"></progress></th>
                  <b id="afajh"><abbr id="afajh"></abbr></b>
                  <th id="afajh"><progress id="afajh"></progress></th>
                  五月天色婷婷综合 | 在线观看你懂的网站 | 精品一二三免费区 | 青娱乐一区二区三区 | 男人v天堂|