나는 일부 코드를 벤치마킹하고 있었고 java.math.BigInteger
정확히 동일한 알고리즘을 사용할 때조차 와 같이 빨리 실행할 수 없었습니다 . 그래서 java.math.BigInteger
소스를 내 패키지에 복사 하고 다음을 시도했습니다.
//import java.math.BigInteger;
public class MultiplyTest {
public static void main(String[] args) {
Random r = new Random(1);
long tm = 0, count = 0,result=0;
for (int i = 0; i < 400000; i++) {
int s1 = 400, s2 = 400;
BigInteger a = new BigInteger(s1 * 8, r), b = new BigInteger(s2 * 8, r);
long tm1 = System.nanoTime();
BigInteger c = a.multiply(b);
if (i > 100000) {
tm += System.nanoTime() - tm1;
count++;
}
result+=c.bitLength();
}
System.out.println((tm / count) + "nsec/mul");
System.out.println(result);
}
}
이것을 실행하면 (MacOS의 경우 JDBC 1.8.0_144-b01) 다음과 같이 출력됩니다.
12089nsec/mul
2559044166
가져 오기 줄을 주석 처리하지 않고 실행할 때 :
4098nsec/mul
2559044166
JDK 버전의 BigInteger를 내 버전과 비교할 때 동일한 코드를 사용하더라도 거의 3 배 빠릅니다.
javap로 바이트 코드를 검사하고 옵션으로 실행할 때 컴파일러 출력을 비교했습니다.
-Xbatch -XX:-TieredCompilation -XX:+PrintCompilation -XX:+UnlockDiagnosticVMOptions
-XX:+PrintInlining -XX:CICompilerCount=1
두 버전 모두 동일한 코드를 생성하는 것 같습니다. 핫스팟은 코드에서 사용할 수없는 사전 계산 된 최적화를 사용합니까? 나는 항상 그렇지 않다는 것을 이해했습니다. 이 차이점을 설명하는 것은 무엇입니까?