2017-12-20 13 views
0

ENUM이 있으며 응용 프로그램 초기화시 해당 열거 형 값을 데이터베이스에서 업데이트하고 있습니다. 그런 다음 해당 열거 형 응용 프로그램을 사용합니다.Java에서 ENUM 값 업데이트

Value가 데이터베이스에서 변경해야하는 경우 속성 테이블에 해당 값을 추가하고 업데이트하면 초기화시 열거 형 값이 업데이트되고 다른 값은 열거 형 기본값이 작동합니다.

예 : 나는이 열거 있습니다

public enum Planet { 
    MERCURY (3.303e+23, 2.4397e6), 
    VENUS (4.869e+24, 6.0518e6), 
    EARTH (5.976e+24, 6.37814e6); 

    private final double mass; // in kilograms 
    private final double radius; // in meters 
    Planet(double mass, double radius) { 
     this.mass = mass; 
     this.radius = radius; 
    } 
    private double mass() { return mass; } 
    private double radius() { return radius; } 

    private void setMass(double mass) { this.mass = mass; } 
    private void setRadius(double radius) { this.radius = radius; } 

} 

을 그리고 설정 방법과 열거의 값을 업데이트합니다.

이 작업이 올바른지 여부를 알고 싶습니다. 그러한 시나리오에 적합한 방법은 무엇입니까?

+0

에서 SerializationUtils 사용할 수 있습니까? –

+0

@AndyTurner 이것은 애플리케이션 속성 값을 가진 내 애플리케이션 사례의 예입니다. –

답변

2

열거 상수는 싱글이고 불변의 객체는 모든 응용 프로그램을 통해 사용할 수 있으며, massradius 필드는 데이터베이스 업데이트에 따라 즉시 변경할 수 없습니다.

대신에 massradius 값을 저장하기 위해 메모리 내 캐시를 만들 수 있으며이 내부 Map은 모든 데이터베이스 업데이트시 새로 고칠 수 있습니다. 그러나 응용 프로그램의 확장 성을 높이려면 내부 캐시 Map 대신 PlanetStats 개체를 저장하는 Redis와 같은 외부 캐시를 사용해야합니다.

enum Planet { 
    MERCURY, 
    VENUS, 
    EARTH 
} 

class PlanetStats { 
    private final double mass; 
    private final double radius; 

    PlanetStats(double mass, double radius) { 
     this.mass = mass; 
     this.radius = radius; 
    } 

    public double getMass() { 
     return mass; 
    } 

    public double getRadius() { 
     return radius; 
    } 
} 


class PlanetCache { 

    private final Map<Planet, PlanetStats> stats = new ConcurrentHashMap<>(); 

    // can be invoked on database update for each Planet object change 
    public void refresh(Planet planet, PlanetStats planetStats) { 
     stats.put(planet, planetStats); 
    } 

    // can be invoked to fetch PlanetStats for specified Planet 
    public PlanetStats getPlanetStats(Planet planet) { 
     return stats.get(planet); 
    } 
} 
1

세터로 업데이트 할 경우 필드는 final이 아니어야합니다.

그게 전부입니다. 다른 주장은 사실이 아닙니다. 이름 지정된 값의 최종 범위가있는 경우 열거 형을 사용하면됩니다.

(최종 필드)을 불변 클래스

더 있었다, 그러나 정적 초기화로하지 않는 한 데이터베이스와 달성하지 않은 것입니다. 초기화하는 동안 데이터베이스를 필요로하는 것은 받아 들일 수 있지만 가능한 경우 및 내장 데이터베이스가 아닌 경우 일반적으로 피해야합니다.

0

열거 형 상태를 변경할 수 있다고해도 나는 추천하지 않습니다.

열거 형은 싱글이며, 이것은 하나 개의 스레드가 상태의 또 다른 변화하면서 열거를 사용할 수 있기 때문에

  1. 당신의 상태 변경, 스레드 안전해야한다는 것을 의미한다.

  2. 다른 개체의 상태와 같이 상태가 serialize되지 않습니다. 직접 또는 다른 프레임 워크 또는 RMI 또는 스프링 리모컨과 같은 기술을 통해 직렬화를 사용하는 경우 상태 변경은 예상대로 작동하지 않습니다.

    예.

    public static void main(String[] args) { 
        Planet mercury = Planet.MERCURY; 
    
        mercury.setMass(1.0); 
    
        byte[] mercurySerialized = SerializationUtils.serialize(mercury); 
    
        mercury.setMass(2.0); 
    
        Planet mercuryDeserialized = SerializationUtils.deserialize(mercurySerialized); 
    
        System.out.println(mercuryDeserialized.mass()); 
    } 
    

    그것은 직렬화 될 때 Planet가 가지고있는 값이없는

    2.0 
    

    직렬화 복원 Planet의 질량 특성을 인쇄합니다.

    또한 블로그의 Singleton implementation pitfalls 섹션에서이 문제를 논의합니다.

PS : 나는 실제로 변경 대중과 행성의 반지름을 수행 평민 - lang3