最近看jvm的一些相關知識,看到i++和++i的指令執行過程,知道的其實也沒啥難的,不知道的估計也說不出為什麼兩個賦值結果不一樣。跟大夥分享分享我的理解。
首先要知道虛擬機器棧是什麼?虛擬機器棧裡都有什麼?此知識點要掌握關於虛擬機器棧中的運算元棧(以下用操作棧代替)和區域性變數表(以下用區域性表代替),還有jvm的基本指令。下面會主要涉及到區域性表和操作棧還有jvm指令這塊的知識。網上一大堆我就不詳細說明了。
public
static
void
main
(string[
] args)
public
static
void
main
(string[
] args)
兩塊**很簡單,就乙個i++的賦值和++i的賦值。很顯然 **1的結果是0,**2的結果是1.為什麼呢?
主要是因為jvm的指令操作不一樣。
**一的jvm執行指令
**2的jvm執行指令
感覺兩個都差不多,區別在哪,區別就在與執行iinc這個指令後的操作。先一步步看
bipush 100: 意思就是將100 壓棧到運算元棧中。
istore_1 :將運算元棧中的棧頂元素(值)存到區域性變數表中的第乙個(index=1)位置,
iinc 1 by 1 :這個看外掛程式,有的地方寫的是 iinc 1,1
意思是將區域性表中的第乙個位置的變數按常量1增加。
第乙個位置1代表索引,第二個1表示常量。
重點來了
iload_1:從區域性表中的第乙個變數的值出棧到運算元棧中。
相當於從區域性表中讀了第乙個資料然後存到操作表中。可以這麼簡單的理解。
區別就在於
i++是直接將操作表中資料存到區域性表中。
而++i是先讀取的區域性表中的資料到操作棧,然後在從操作棧存到區域性表中。
為什麼這樣做?主要是因為iinc這個命令,這個命令是操作的是區域性表。
i++:
iinc 執行之前是 區域性表中變數值是100的而操作棧裡的值也是100.
但是執行完iinc命令後是區域性表中值變成101,而操作棧中的值依然是100;最後執行istore區域性表變100.
++i:
iinc執行之前是區域性表中變數值是100,而操作棧裡是空的。
iinc執行完後區域性表中是101,由於執行了iload操作棧也是101.最後執行了istore最終區域性表變101.
但是上面的**都是有 「=」 符號的。假如沒有「=」 符號會發生什麼。
當你不做任何賦值的時候++i和i++是沒有區別的。當賦值的時候才會存在區別。
i++和++i最終的區別其實就在於有沒有去讀區域性表中的變數的值。
小白第一次寫部落格,說的寫的不對的,有錯誤的請指出,一起**,盡快做修正,以免誤導別人。
感謝大家!!!
從jvm棧幀中區別i 和 i
有關jvm的一些詳細內容我就不在贅述,那麼到底i 和 i的區別體現在 呢?從位元組碼上來看,i 是iload,iinc,而 i是iinc,iload iload是從區域性變數表中載入int型別的資料到操作棧中 iinc是int變數的增值變化,是在區域性變數表中自增的 istore是將操作棧頂的int...
i和i 的區別
大家都應該知道i 和 i的區別,前者是先使用i的值,然後再增加1,而後者是先增加1然後再使用i的值。但是i 和 i那個更好呢?我們實現角度來看 前者是將i值加1後賦給i,然後返回i本身 而後者是先用個臨時變數儲存i值,然後將i值加1賦給i,然後返回臨時變數的值。內建資料型別他們的效率差不多,看他們的...
i 和 i的區別
當年上c 課的時候對於i 和 i的區別就稀里糊塗。後來沒注意也沒出過什麼問題。但是這個問題還是應該搞清楚。假如有乙個vector,值為 1,2,3,4,5,6,7 用以下程式輸出 i 0 while i 7 i 0 while i 7 cout beforei v i endl cout befor...