2012-01-02 3 views
0

java에서 컴파일과 런타임 계산을 이해하려고합니다. 나는 방향과 MapLocations의 배열 사이에 일정한 매핑을 정의하려면, 즉 다음 열거java 컴파일 - 런타임 계산

public enum SightSensor{ 

    NORTH (new MapLocation[]{new MapLocation(0,1), 
         new MapLocation(0,2), 
         new MapLocation(0,3)}), 
    SOUTH (new MapLocation[]{new MapLocation(0,-1), 
         new MapLocation(0,-2), 
         new MapLocation(0,-3)}); 

    private final MapLocation[] locs; 

    SightSensor(MapLocation[] locs){ 
    this.locs = locs; 
    } 

    public static MapLocation[] getLocs(Direction dir){ 
    if (dir == Direction.NORTH) 
     return NORTH.locs; 
    if (dir == Direction.SOUTH) 
     return SOUTH.locs; 
    } 
}; 

있습니다. (아마도 이것이 내가 자바에 새로운 해요?이 작업을 수행하는 잘못된 방법입니다.) 자,이 코드에서 루프 내에서

MapLocation[] locs = SightSensor.getLocs(Direction.SOUTH_WEST); 

쓰기 경우, 나는 비용이 오버 헤드 처음이 있다는 것을 발견 코드 이 호출되어 런타임에 계산되고 인스턴스화되는 것을 의미합니다. 대신 경우 그냥 직접에는 비용 부담이 없다

MapLocation[] locs = new MapLocation[]{new MapLocation(0,1), 
          new MapLocation(0,2), 
          new MapLocation(0,3)}; 

코드입니다. 차이점을 이해하지 못합니다. 컴파일러에서 just-in-time 계산의 이상한 종류 인 을 수행합니까?

+0

비용 오버 헤드를 측정하는 방법을 설명 할 수 있습니까? –

+0

또한 예제가 컴파일되지 않습니다. 'dir'이 NORTH도 SOUR도 아닌 경우) –

+0

네일, 죄송합니다. 코드를 단순화하려고 시도 했으므로 반환 값이없는 경로가 있기 때문에 getLocs에서 else 문이 필요합니다. 바이트 코드로 측정. – andyInCambridge

답변

3

처음 보는 코드가 클래스에 액세스 할 때 클래스 로더는 이진 파일 (.class 파일)을 메모리에로드합니다. 이것은 대부분의 실제적인 목적을 위해 무시할 수있는 1 회성 비용입니다. 또한

: 이제

, 내가 쓰는 경우 ... 코드에서 루프 내부에, 나는

방법, 오버 헤드 비용 코드가 처음 호출이 있음을 발견 이 비용을 측정 했습니까? 단일 작업의 시간 비용을 측정하는 것은 거의 불가능합니다. 루프를 통해 xM 패스를 수행하는 데 필요한 시간을 측정 한 다음 나누어서 상각 된 비용을 얻을 수 있습니다. 그러나 단일 작업을 측정하는 것은 어렵습니다. 가비지 수집주기, 스레드 관련 컨텍스트 스위치 등이있을 수 있습니다. 또한 JIT (Just In Time) 컴파일러는 명령문이 처음 실행될 때 실행되지 않으므로 측정 단일 작업으로 N 작업보다 상각 된 비용보다 훨씬 높은 비용이 발생합니다.

EnumMap<Direction, MapLocation[]> map = new EnumMap(Direction.class); 
map.put(Direction.NORTH, new MapLocation[] { new MapLocation(0, 1), 
               new MapLocation(0, 2), 
               new MapLocation(0, 3) }); 
map.put(Direction.NORTH, new MapLocation[] { new MapLocation(0, -1), 
               new MapLocation(0, -2), 
               new MapLocation(0, -3) }); 

그런 다음, getLocs() 전화는 단순히 map.get(dir) 될 :

public static MapLocation[] getLocs(Direction dir) { 
    return valueOf(dir.name()).locs; 
} 

을 또는 당신 형 EnumMap는의 변수로 SightSensor 열거를 대체 사용할 수 있습니다, 다음과 같이

FWIW, 내가 getLocs()를 작성합니다

+0

실제로 바이트 코드의 비용을 측정하고 있으므로 타이밍은 문제가 아니지만 컴파일 방법이 다릅니다. – andyInCambridge

+0

바이트 코드에서 어떤 종류의 비용이 발생합니까? –

+0

약 10000 바이트 코드 – andyInCambridge

2

컴파일러가 저스트 인 타임 계산을 수행합니까?

예, 자바 런타임은 실행되는 코드를 최적화하기 위해 통계를 사용하지 않습니다 그것에 대해 이상한

http://docs.oracle.com/javase/6/docs/technotes/tools/share/jstat.html

아무것도.

뿐만 아니라 관련의 될 수 있습니다

Real differences between "java -server" and "java -client"?

가 개인적으로, 나는 당신이 코드는 가능한 읽기 및 최적화에 대한 걱정하기 쉽도록 작성해야합니다 생각합니다. 속도 향상은 아마도 중요하지 않습니다.

+0

답장을 보내 주셔서 감사합니다. 나는 C++에서 왔으므로 아직 이러한 세부 사항을 인식하지 못했습니다. – andyInCambridge

0

이것은 실제로 대답이 아니지만 팁이됩니다. getLocs을 비 정적으로 설정하면됩니다. 현재 열거의 locs :

public MapLocation[] getLocs(){ 
    return locs; 
} 

대신 SightSensor.getLocs(someDir) 당신은 다음 someDir.getLocs()를 호출합니다.

이렇게하면 열거 형의 모든 구성원을 열거하지 않아도됩니다.