<ruby id="bdb3f"></ruby>

    <p id="bdb3f"><cite id="bdb3f"></cite></p>

      <p id="bdb3f"><cite id="bdb3f"><th id="bdb3f"></th></cite></p><p id="bdb3f"></p>
        <p id="bdb3f"><cite id="bdb3f"></cite></p>

          <pre id="bdb3f"></pre>
          <pre id="bdb3f"><del id="bdb3f"><thead id="bdb3f"></thead></del></pre>

          <ruby id="bdb3f"><mark id="bdb3f"></mark></ruby><ruby id="bdb3f"></ruby>
          <pre id="bdb3f"><pre id="bdb3f"><mark id="bdb3f"></mark></pre></pre><output id="bdb3f"></output><p id="bdb3f"></p><p id="bdb3f"></p>

          <pre id="bdb3f"><del id="bdb3f"><progress id="bdb3f"></progress></del></pre>

                <ruby id="bdb3f"></ruby>

                合規國際互聯網加速 OSASE為企業客戶提供高速穩定SD-WAN國際加速解決方案。 廣告
                [TOC] ##### 一、CPU時間片 * CPU時間片即CPU分配給每個線程的執行時間段,稱作它的時間片。CPU時間片一般為幾十毫秒(ms)。 ##### 二、什么是上下文切換 CPU通過時間片段的算法來循環執行線程任務,而循環執行即每個線程允許運行的時間后的切換,而這種循環的切換使各個程序從表面上看是同時進行的。而切換時會保存之前的線程任務狀態,當切換到該線程任務的時候,會重新加載該線程的任務狀態。而這個從保存到加載的過程稱之為上下文切換。 * 若當前線程還在運行而時間片結束后,CPU將被剝奪并分配給另一個線程。 * 若線程在時間片結束前阻塞或結束,CPU進行線程切換。而不會造成CPU資源浪費。 ##### 三、上下文切換造成的影響 我們可以通過對比串聯執行和并發執行進行對比。 ~~~ private static final long count = 1000000; public static void main(String[] args) throws Exception { concurrency(); series(); } /** * 并發執行 * @throws Exception */ private static void concurrency() throws Exception { long start = System.currentTimeMillis(); //創建線程執行a+= Thread thread = new Thread(new Runnable() { public void run() { int a = 0; for (int i = 0; i < count; i++) { a += 1; } } }); //啟動線程執行 thread.start(); //使用主線程執行b--; int b = 0; for (long i = 0; i < count; i++) { b--; } //合并線程,統計時間 thread.join(); long time = System.currentTimeMillis() - start; System.out.println("Concurrency:" + time + "ms, b = " + b); } /** * 串聯執行 */ private static void series() { long start = System.currentTimeMillis(); int a = 0; for (long i = 0; i < count; i++) { a += 1; } int b = 0; for (int i = 0; i < count; i++) { b--; } long time = System.currentTimeMillis() - start; System.out.println("Serial:" + time + "ms, b = " + b + ", a = " + a); } ~~~ 通過修改循環次數,對比串行運行和并發運行的時間測試結果: | 循環次數 | 并發執行時間 | 串聯執行時間 | | --- | --- | --- | | 一百萬 | 2ms | 4ms | | 十萬 | 2ms | 2ms | | 一萬 | 1ms | 0ms | 通過數據的對比我們可以看出。在一萬以下的循環次數時,串聯的執行速度比并發的執行速度塊。是因為線程上下文切換導致額外的開銷。 在Linux系統下可以使用vmstat命令來查看上下文切換的次數,如果要查看上下文切換的時長,可以利用Lmbench3,這是一個性能分析工具。 #### 四、如何減少上下文切換導致額外的開銷 減少上下文切換次數便可以提高多線程的運行效率。減少上下文切換的方法有無鎖并發編程、CAS算法、避免創建過多的線程和使用協程。 * 無鎖并發編程.當任何特定的運算被阻塞的時候,所有CPU可以繼續處理其他的運算。換種方式說,在無鎖系統中,當給定線程被其他線程阻塞的時候,所有CPU可以不停的繼續處理其他工作。無鎖算法大大增加系統整體的吞吐量,因為它只偶爾會增加一定的交易延遲。大部分高端數據庫系統是基于無鎖算法而構造的,以滿足不同級別。 * CAS算法。Java提供了一套原子性操作的數據類型(java.util.concurrent.atomic包下),使用CAS算法來更新數據,不需要加鎖。如:AtomicInteger、AtomicLong等。 * 避免創建過多的線程。如任務量少時,盡可能減少創建線程。對于某個時間段任務量很大的這種情況,我們可以通過線程池來管理線程的數量,避免創建過多線程。 * 協程:即協作式程序,其思想是,一系列互相依賴的協程間依次使用CPU,每次只有一個協程工作,而其他協程處于休眠狀態。如:JAVA中使用wait和notify來達到線程之間的協同工作。 參考: 《Java并發編程的藝術》
                  <ruby id="bdb3f"></ruby>

                  <p id="bdb3f"><cite id="bdb3f"></cite></p>

                    <p id="bdb3f"><cite id="bdb3f"><th id="bdb3f"></th></cite></p><p id="bdb3f"></p>
                      <p id="bdb3f"><cite id="bdb3f"></cite></p>

                        <pre id="bdb3f"></pre>
                        <pre id="bdb3f"><del id="bdb3f"><thead id="bdb3f"></thead></del></pre>

                        <ruby id="bdb3f"><mark id="bdb3f"></mark></ruby><ruby id="bdb3f"></ruby>
                        <pre id="bdb3f"><pre id="bdb3f"><mark id="bdb3f"></mark></pre></pre><output id="bdb3f"></output><p id="bdb3f"></p><p id="bdb3f"></p>

                        <pre id="bdb3f"><del id="bdb3f"><progress id="bdb3f"></progress></del></pre>

                              <ruby id="bdb3f"></ruby>

                              哎呀哎呀视频在线观看