java代碼是否一定按順序執行? 這個問題聽起來有點蠢,串列的代碼確實會按代碼語意正確的執行,但是編譯器對於代碼本身的優化卻並不一定會按實際的代碼一步一步的執行。 比如: r1=a; r2=r1.x; r3=r1.x; 編譯器則可能會進行優化,將r3=r1.x這條指令替換成r3=r2,這就是指令的重 ...
java代碼是否一定按順序執行?
這個問題聽起來有點蠢,串列的代碼確實會按代碼語意正確的執行,但是編譯器對於代碼本身的優化卻並不一定會按實際的代碼一步一步的執行。
比如:
r1=a;
r2=r1.x;
r3=r1.x;
編譯器則可能會進行優化,將r3=r1.x這條指令替換成r3=r2,這就是指令的重排
編譯器為什麼要做指令的重排呢?
地球人都知道,當然是出於性能上的考慮,而指令重排能提升多少性能?
首先指令的執行可以分為這幾步:
- 取指 IF
- 解碼和取寄存器操作數 ID
- 執行或者有效地址計算 EX (ALU邏輯計算單元)
- 存儲器訪問 MEM
- 寫回 WB (寄存器)
詳見:https://blog.csdn.net/fuhanghang/article/details/83421254
而一段代碼並不是由單條指令就可以執行完畢的,而是通過流水線來執行多條指令。
流水線技術是一種將指令分解為多步,並讓不同指令的各步操作重疊,從而實現幾條指令並行處理。
指令1 IF ID EX MEN WB
指令2 IF ID EX MEN WB
指令的每一步都由不同的硬體完成,假設每一步耗時1ms,執行完一條指令需耗時5ms,
每條指令都按順序執行,那兩條指令則需10ms。
但是通過流水線在指令1剛執行完IF,執行IF的硬體立馬就開始執行指令2的IF,這樣指令2只需要等1ms,兩個指令執行完只需要6ms,效率是不是提升巨大!
先記住幾個指令:
MIPS彙編指令集---https://www.cnblogs.com/yanghong-hnu/p/5635245.html
LW(載入數據到寄存器的指令)
ADD(兩個定點寄存器的內容相加)
SUB(相減)
SW(把數據從寄存器存儲到存儲器)
現在來看一下代碼 A=B+C 是怎麼執行的
現有R1,R2,R3三個寄存器,
LW R1,B IF ID EX MEN WB(載入B到R1中)
LW R2,C IF ID EX MEN WB(載入C到R2中)
ADD R3,R2,R1 IF ID × EX MEN WB(R1,R2相加放到R3)
SW A,R3 IF ID x EX MEN WB(把R3 的值保存到變數A)
在ADD指令執行中有個x,表示中斷、停頓,ADD為什麼要在這裡停頓一下呢?因為這時C還沒載入到R2中,只能等待,而這個等待使得後邊的所有指令都會停頓一下。
這個停頓可以避免嗎?
當然是可以的,通過指令重排就可以實現,再看一下下麵的例子:
要執行
A=B+C;
D=E-F;
通過將D=E-F執行的指令順序提前,從而消除因等待載入完畢的時間。
LW Rb,B IF ID EX MEN WB
LW Rc,C IF ID EX MEN WB
LW Re,E IF ID EX MEN WB
ADD Ra,Rb,Rc IF ID EX MEN WB
LW Rf,F IF ID EX MEN WB
SW A,Ra IF ID EX MEN WB
SUB Rd,Re,Rf IF ID EX MEN WB
SW D,Rd IF ID EX MEN WB