클래스는 언제 로딩될까
클래스 로딩?
클래스 로더가 .class파일을 찾아 JVM의 메모리에 올려놓는 과정을 의미한다.
로딩 종류
1. 로드타임 동적 로딩
2. 런타임 동적 로딩
두 로딩에 대한 설명은 JVM 동적 클래스 로딩 (tistory.com) 블로그를 참고 바랍니다.
클래스 로딩 시점
- 클래스의 인스턴스 생성
- 클래스의 정적 메소드 호출
클래스의 정적 변수 사용 (final x)---> ? 타입에 따라 달랐다. String, 정의한 클래스 두개로 테스트 진행!- 데이터타입이 클래스 타입인 경우로 정적 변수 사용(final 유무 관계없이)
클래스 로딩 확인 방식( 나는 CMD창에서 진행함 )
1. java파일 컴파일
2. java -vervbose:class class파일명
<예시>
javac Main.java
java -vervbose:class Main
1. 클래스의 인스턴스 생성
public class Main {
public static void main(String[] args) {
//클래스 인스턴스 생성
TestClass testClass = new TestClass();
}
}
class TestClass{
public String test;
}
2. 클래스의 정적 메소드 호출
public class Main {
public static void main(String[] args) {
Singleton.getInstance() //정적메소드 호출
}
}
class Singleton{
//정적 메소드
static void getInstance(){
System.out.println("정적메소드 호출!");
}
}
3. 클래스의 정적 변수 사용(final 키워드 사용 X)
public class Main {
public static void main(String[] args) {
System.out.println(Singleton.INSTANCE); //정적 변수 사용
}
}
class Singleton{
//정적 변수
static Singleton INSTANCE = new Singleton();
}
4. 클래스의 정적 변수 사용(final 키워드 사용)
클래스 로딩 시점 중 final키워드를 사용하면 클래스가 로딩되지 않는다는 글을 봐 눈으로 직접 확인해 보려 한다.
테스트케이스1) final 키워드 사용 && 클래스타입 변수
테스트케이스2) final 키워드 사용 && String형 변수(기본형으로 생각하면 될 듯)
결론부터 말한다면,
class타입인 경우 Singlton 클래스 호출 O
String타입인 경우 Singlteon 클래스 호출 X
컴파일된 클래스 파일을 디컴파일한 부분을 자세히 봐보자.
4.1 class타입
public class Main {
public static void main(String[] args) {
System.out.println(Singleton.INSTANCE);
}
}
class Singleton{
//fianl 선언된 클래스타입 정적 변수
static final Singleton INSTANCE = new Singleton();
}
4.2 String 타입
public class Main {
public static void main(String[] args) {
System.out.println(Singleton.INSTANCE);
}
}
class Singleton{
//fianl 선언된 String형 정적 변수
static final String INSTANCE = "test";
}
엥???
String인 경우 코드상과 컴파일된 내용을 디컴파일한 내용과 다르다!!!!!! System.out.println("test") ???
난 분명 코드 작성 시 System.out.println(Singlton.instacne)로 적었는데?
컴파일 되고 보니 값으로 바껴있다...?
아! 컴파일 시점에 Singleton.INSTACNE를 "test"로 바꿨구나!!!!!!
위 두 테스트 케이스를 결론으로 이야기를 해본다면,
* String의 경우는 Sinlgton클래스를 로딩하지도 않으며, 컴파일 시점에서 어딘가에 참조하는 상수(Singlton.Instance)를 값("test)으로 바로 할당하는 것으로 보인다. (참고. final로 선언된 상수 컴파일에 관하여 (tistory.com))
* 이와 반대로, class타입의 경우는 singlton클래스를 로딩하며, 컴파일 시점엔 기존코드와 컴파일시점에서의 코드가 동일하다.
final키워드를 사용하면 클래스가 로딩되지 않는다???
아니다. final키워드를 사용해도 데이터 타입에 따라 클래스 로딩이 결정된다.
참고