http://cafe.naver.com/swnara/369
http://kevinx64.net/107
개발하다보면 종종 serialVersionUID를 보게된다. 이값은 어디에 사용하는것일까 궁금해서 찾아보게 되었다.
Serialize (직렬화)
객체를 파일로 저장하거나, 혹은 다른 사람에서 전송하기 위해서는 직렬화(serialize) 및 역직렬화(deserialize)가 필요하다.
직렬화란 메모리나 저장공간에 담을 수 있도록 일렬로 만드는 것을 의미하며, 직렬화를 해야만 객체를 저장하거나 통신할 수 있다.
Serializable 인터페이스는 구현 메소드, 필드가 없는 껍데기 인터페이스로 JAVA에서는 이 인터페이스를 구현하여 직렬화가 가능한 객체임을 인식한다.
Serializable을 구현한 객체를 저장하면 해당 class에 정의된 private을 포함한 모든 필드와 값, super class의 모든 필드 및 값이 저장된다.
SerialVersionUID
Serializable 인터페이스를 구현하게되면 IDE에서 serialVersionUID를 생성하도록 warning을 표시한다. 이 SerialVersionUID는 무엇에 쓰이는것일까? 그리고 해당 값을 선언하지 않으면 어떻게 되는것일까?
http://kevinx64.net/107 에서 이 의문에 대한 답을 찾을 수 있었다.
직렬화 가능(Serializable) 클래스가 serialVersionUID를 명시적으로 선언하지 않는 경우, 직렬화 런타임은 「Java(TM) 객체 직렬화 스펙」에서 설명하고 있듯이, 클래스의 다양한 측면에 근거해, 클래스의 serialVersionUID의 Default 값를 계산한다. 다만, 모든 직렬화 가능 클래스가 serialVersionUID를 명시적으로 선언하는 것을 강하게 추천한다. Default의 serialVersionUID 계산이, 컴파일러의 구현에 따라서, 다를 가능성이 있는 클래스의 영향을 받기 쉽고, 직렬화 복원 중에 예기치 않은 InvalidClassException 가 발생할 가능성이 있기 때문이다. 따라서, java 컴파일러의 구현이 달라도 serialVersionUID의 일관성을 확보로 하려면, 직렬화 가능 클래스가 serialVersionUID를 명시적으로 선언하지 않으면 안된다. 또, serialVersionUID 의 명시적인 선언에서는 private 수식자를 사용하는 것을 적극 추천한다. 이러한 선언은 직접적으로 선언하는 클래스에게만 적용되게 하기 위한 것이다. private으로 선언하면, serialVersionUID 필드를 상속되는 멤버와 같이 사용하지 않는다.
SerialVersionUID는 객체 직렬화 시에 동일한 Class 명을 갖고있더라도 실제로 동일한 class가 맞는지 검사하기 위해 version을 지정하는것이며, 이 값을 명시적으로 지정하지 않으면 JVM은 default로 serialVersionUID를 계산하여 사용한다.
여러가지 근거를 통해 자동으로 serialVersionUID를 계산해 낼 때 환경적인 사유 혹은 불특정한 이유로 인해 이 값이 다르게 계산될 수도 있으며, 이 경우 InvalidClassException이 발생할 수 있으므로 명시적으로 선언해주는것을 권장한다.
Transient
직렬화 시에 대상에서 제외하고 싶은 경우 변수 선언 앞에 transient를 선언하면 직렬화 대상에서 제외가 된다.
'development > Java' 카테고리의 다른 글
[도서] Java8 in Action - 새로운 날짜/시간 API (0) | 2017.04.25 |
---|---|
[도서] Java8 in Action - Stream (0) | 2017.04.25 |