2011-11-18 3 views
8

호기심에서 정적 블록과 정적 메서드 초기화 프로그램 간의 성능을 측정했습니다. 첫째, 두 개의 분리 된 자바 클래스에서 전술 한 방법을 구현하므로 같은정적 블록 대 정적 메소드 - 정적 필드 초기화

첫째

class Dummy { 
    static java.util.List<Integer> lista = new java.util.ArrayList<Integer>(); 
    static { 
     for(int i=0; i < 1000000; ++i) { 
      lista.add(new Integer(i)); 
     } 
    } 
} 

public class First { 
    public static void main(String[] args) { 
     long st = System.currentTimeMillis(); 
      Dummy d = new Dummy(); 
     long end = System.currentTimeMillis() - st; 
     System.out.println(end);  
    } 
} 

둘째

class Muddy { 
    static java.util.List<Integer> lista = new java.util.ArrayList<Integer>(); 
    public static void initList() { 
     for(int i=0; i < 1000000; ++i) { 
      lista.add(new Integer(i)); 
     } 
    } 
} 

public class Second { 
    public static void main(String[] args) { 
     long st = System.currentTimeMillis(); 
      Muddy.initList(); 
      Muddy m = new Muddy(); 
     long end = System.currentTimeMillis() - st; 
     System.out.println(end);  
    } 
} 

그럼 I가 100을 측정하는 this 작은 배치 스크립트 실행 시간을 계산하고 값을 파일에 저장하십시오. batchFile.bat First Second dum.res.txt

그 후 나는 더미와 머디의 측정 값의 평균값과 표준 편차를 계산하기 위해 코드 조각을 this 작성했습니다.

내가있어 결과입니다 :

First size: 100 Second size: 100 
First  Sum: 132 Std. deviation: 13 
Second  Sum: 112 Std. deviation: 9 

그리고 ... 나는 그것을 테스트 할 때마다 내 다른 컴퓨터에서 유사하다.

지금 나는 왜 그렇게 생각합니까? 바이트 코드를 확인하고 Second.class에 System.currentTimeMillis() 호출 사이에 하나의 명령어가 더 있습니다 (정적 initList() 호출). 둘 다 똑같은 일을하지만 왜 첫번째 것이 더 느린가? 이것이 바이트 코드를 보았을 때 나는 그것을 처음으로 만지작 거리고있다. javap; 나는 아직 바이트 코드를 이해하지 못한다.

+0

일괄 처리 스크립트 호출에서 첫 번째와 두 번째를 뒤집어서 결과가 무엇인지 확인해보십시오. – antlersoft

+0

명령어 수는 해당 명령어의 소요 시간과 아무 관련이 없습니다. 글쎄, 너가 Lichenstein 또는 무언가에서 살지 않는 한). 똑같은 지침입니까? 나는 그것을 의심한다. 보조 노트에서, 두 번째 버전을 사용하는 것이 주저 할 것입니다. 더 빨라지더라도, 'initList()'호출을 사용하는데 의존하지 않습니다. –

+0

@antlersoft 동일한 결과를 반환합니다. 이미 테스트를 마쳤습니다. – Mechkov

답변

2

나는 정적 블록 버전으로 인해 그들이 얻을 다른 JIT 최적화에 정적 메소드 버전이 될 수있는 것보다 느린 이유 ...

가 더 흥미로운 내용은이 흥미로운 기사를 참조 생각 : Java Secret: Are static blocks interpreted?

2

여기에 대한 이유는 다음과 같습니다.

초기화 작업은 하나 이상의 가비지 수집을 일으키는 충분한 개체를 만드는 것입니다.

초기화가 정적 블록에서 호출되면 단순 메소드 실행 중에가 아니라 클래스 초기화 중에 초기화가 수행됩니다. 클래스 초기화 중에는 힙의 내용이 거의 같더라도 가비지 감지기가 간단한 메소드 실행 중에 비해 실행 작업이 더 길기 때문에 수행해야 할 작업이 조금 더있을 수 있습니다.

이것을 테스트하려면 java 명령에 -Xms200m 또는 뭔가를 추가해보십시오. 이렇게하면 초기화하는 동안 가비지 수집 할 필요가 제거됩니다.