작업을 수행하기 위해 생성된 Java 코드가 "인터프리터 루프"보다 느리게 실행되는 이유는 무엇입니까?

StackOverflow https://stackoverflow.com/questions/875695

문제

BitSet에서 비트 연산을 수행하는 Java 코드가 있습니다.작업 목록이 있고 이를 반복하여 "해석"할 수 있지만 이러한 작업을 가능한 한 빨리 수행할 수 있는 것이 중요하므로 해당 작업을 적용하기 위한 코드를 동적으로 생성하려고 노력해 왔습니다.작업을 수행하기 위한 Java 소스를 생성하고 Javassist를 사용하여 해당 작업을 구현하는 클래스를 컴파일합니다.

불행하게도 동적으로 생성된 코드는 해석된 코드보다 느리게 실행됩니다.이는 HotSpot이 해석된 코드를 최적화하지만 컴파일된 코드는 최적화하지 않기 때문인 것 같습니다.수천 번 실행한 후에 해석된 코드는 처음보다 두 배 빠르게 실행되지만 컴파일된 코드에서는 속도 향상이 나타나지 않습니다.이 가설에 따라 해석된 코드는 처음에는 컴파일된 코드보다 느리지만 결국에는 더 빨라집니다.

왜 이런 일이 발생하는지 잘 모르겠습니다.내 생각엔 아마도 Javassist가 HotSpot 클래스가 건드리지 않는 클래스 로더를 사용하는 것 같습니다.하지만 저는 Java의 클래스 로딩 전문가가 아니기 때문에 이것이 합리적인 추측인지 또는 테스트 방법을 잘 모르겠습니다.Javassist를 사용하여 클래스를 생성하고 로드하는 방법은 다음과 같습니다.

ClassPool pool = ClassPool.getDefault();
CtClass tClass = pool.makeClass("foo");

// foo implements MyInterface, with one method
tClass.addInterface(pool.get(MyInterface.class.getName()));

// Get the source for the method and add it
CtMethod tMethod = CtNewMethod.make(getSource(), tClass);
tClass.addMethod(tMethod);

// finally, compile and load the class
return (MyInterface)tClass.toClass().newInstance();

여기서 무슨 일이 일어나고 있는지 아는 사람이 있나요?어떤 도움을 주셔도 정말 감사하겠습니다.

저는 Windows XP 32비트에서 Sun 1.6 서버 JVM을 사용하고 있습니다.

도움이 되었습니까?

해결책

핫스팟은 코드의 출처를 신경 쓰지 않습니다. 예를 들어, 다른 클래스 로더가로드 한 구현과 함께 가상 메소드 호출을 통해 호출 된 인라인 코드가 행복하게 나타납니다.

이 벤치 마크에서 수행하려는 작업을 소스 코드로 작성한 다음 벤치마킹하는 것이 좋습니다. 어쨌든 발전기를 쓰지 않고 생성 된 코드의 예를 작성하는 것이 일반적으로 더 쉽습니다.

핫스팟이 코드를 최적화 할 수없는 많은 이유가 있습니다. 예를 들어, 매우 긴 방법은 감소되지 않거나 방법이 내려지는 경향이 있습니다.

다른 팁

나는 여기서 무슨 일이 있었는지 이해한다고 생각합니다. 나의 첫 번째 실수는 너무 긴 방법을 생성하는 것이 었습니다. 그것을 고쳤을 때, 나는 생성 된 코드가 여전히 느려졌지만 결국 해석 된 코드의 속도에 접근했다는 것을 알았습니다.

여기에서 가장 큰 속도는 내 코드를 최적화하는 핫스팟에서 나온다고 생각합니다. 해석 된 버전에는 최적화 할 코드가 거의 없으므로 핫스팟이 신속하게 처리합니다. 생성 된 버전에는 최적화 할 코드가 많이 있으므로 핫스팟은 모든 코드보다 마법을 작동하는 데 시간이 오래 걸립니다.

벤치 마크를 충분히 오래 실행하면 이제 생성 된 코드가 해석 된 코드보다 약간 더 잘 수행되는 것을 볼 수 있습니다.

코드를 얼마나 빨리 컴파일해야 하는지 제어하는 ​​JVM 설정이 있습니다. -XX:CompileThreshold=10000

컴파일 전 메소드 호출/분기 수 [-client:1,500]

이것이 도움이 될지 모르겠습니다. 귀하의 예에서는 크기가 중요한 역할을 하는 것 같기 때문입니다.

라이센스 : CC-BY-SA ~와 함께 속성
제휴하지 않습니다 StackOverflow
scroll top