ØGroovy的大師,Groovy的for循環執行時間
這段代碼運行在1秒左右
for (int i in (1..10000000)) {
j = i;
}
,而這其中需要近9秒
for (int i = 1; i < 10000000; i++) {
j = i;
}
爲什麼會這樣呢?
ØGroovy的大師,Groovy的for循環執行時間
這段代碼運行在1秒左右
for (int i in (1..10000000)) {
j = i;
}
,而這其中需要近9秒
for (int i = 1; i < 10000000; i++) {
j = i;
}
爲什麼會這樣呢?
好的。這是我的理由爲什麼?
如果都轉換腳本字節碼,你會發現,
ScriptBytecodeAdapter .compareLessThan - >ScriptBytecodeAdapter .compareTo - >DefaultTypeTransformation .compareTo
有其他類typehandling包特異性實現compareTo方法的數學數據類型,不知道爲什麼在不使用它們,(如果未使用它們)
我懷疑這是第二個循環需要更長時間的原因。 再一次請糾正我,如果我錯了或丟失東西...
在測試中,確保在採取措施之前先對JVM進行「加熱」,否則可能會觸發平臺中的各種啓動操作(類加載,JIT編譯)。也連續多次運行您的測試。另外,如果您在進行垃圾收集時進行了第二次測試,那可能會產生影響。嘗試運行每個測試100次,並在每次測試後打印出時間,並查看告訴你的內容。
如果您可以根據Jim的建議消除啓動時潛在的工件,那麼我會猜測Groovy中的Java風格的for循環沒有像原始的Groovy風格的for循環那麼好實現。它只是在用戶請求後才添加到v1.5中,所以它的實現可能有點後事。
您是否看過爲您的兩個示例生成的字節碼,以查看是否有區別?有一個關於Groovy性能here其中一個評論(從一個「johnchase」)說,這個討論:
不知的區別你看到了相關的用途如何Groovy的數量(元) - 因爲它包裝所有的原語在他們的等價的Java包裝類(int - > Integer)中,我想這會讓事情減慢很多。我會對使用包裝類而不是int進行循環10,000,000次Java代碼的性能感興趣。
所以也許最初的Groovy for循環不會受到這個?只是猜測我的角色。
小福,這些都是好點。我感到困惑的是底部循環應該是更快的,因爲它只處理整數,而不是整數(儘管j的類型沒有指定)。給定順序,頂部循環應該更慢。 – 2009-05-28 15:24:09
這幾乎可以肯定地解釋它。我知道Java風格的for循環爲您提供了更多的靈活性,但它們肯定可以對最基本的(也是最常用的)形式應用一些優化,以便它可以像for..in循環一樣執行?對於從Java或C#來的人來說,這是一個很小的性能陷阱... – Xiaofu 2009-05-30 05:30:53