자바의 정석 7장에 나오는 package와 import에 대한 내용입니다. 기본적인 내용이지만 평소에는 IDE의 도움을 빌리고 있다보니 정확히 어떤 의미인지 모르고 사용하는 것 같아 정리 차 올려봅니다. 잘못된 내용이 있다면 댓글 남겨주시면 감사하겠습니다 :)
자바의 패키지란, 클래스의 묶음이다. 패키지에는 클래스 또는 인터페이스를 포함시킬 수 있으며, 서로 관련된 클래스들끼리 그룹 단위로 묶어 놓음으로써 클래스를 효율적으로 관리할 수 있다.
지금까지는 단순히 클래스 이름으로만 클래스를 구분했지만, 사실 클래스의 실제 이름은 패키지 명을 포함한 것이다.
(ex. String 클래스는 java.lang.String이다.)
패키지끼리는 '.'을 통해 하위패키지를 구분하고 있으며, 위 String 클래스는 java 패키지 하위의 lang 패키지에 들어있는 클래스인 것이다.
패키지의 선언은 소스 코드 맨 위에 패키지의 경로를 적어주면 된다. 만약 패키지 선언을 하지 않으면 unnamed package에 포함되고, 선언되지 않은 패키지들이 모두 한 패키지에 모이게 된다.
그런데, 위 코드의 package 선언을 보면 패키지의 경로가 Main.ch2인 것을 알 수 있다. 실제로는 /Users/Seyeong/Documents/Study-2022/StandardOfJava/src/Main/ch2와 같은 경로를 가지는데, 앞의 경로가 생략된 것은 IntelliJ에서 classpath로 앞의 경로를 지정해주었기 때문이다. 즉, 컴파일 시 해당 경로에서 명시한 패키지 이름을 찾아가는 것이다.
소스 코드를 작성할 때 다른 패키지의 클래스를 사용하려면 패키지명이 포함된 클래스를 사용해야 한다. 예를 들어, List를 사용하려면 java.util.List와 같은 형태로 적어주어야 한다.
이렇게 자주 사용되는 다른 패키지의 클래스를 사용할 때마다 적어주어야 한다면 매우 불편할 것이다. 그래서 java는 import를 통해 사용할 패키지의 클래스를 명시해줄 수 있다. 컴파일러로 하여금 이 클래스의 패키지 경로를 알 수 있도록 선언해주는 것이다.
추가로, java.lang 패키지는 일반적으로 많이 사용되는 패키지가 모여있다. (String, System, Thread 등) 그렇기 때문에, 이 java.lang 패키지의 모든 클래스는 기본적으로 import 되어있는 상태이다. 즉, import 문이 생략되어있다.
그리고 패키지명.*와 같이 해당 패키지의 모든 class를 import할 수 있지만, 이것은 컴파일 단계에서 처리되기 때문에 성능과 직결되는 요소는 아니라고 한다. 물론 컴파일 시간이 오래걸릴 수는 있다.
static import는 static 멤버를 호출할 때 클래스 이름을 생략할 수 있게 해주는 명령어이다. 예를 들어, Math.random이나 System.out같은 static 멤버가 접근하려면, 꼭 앞에 클래스이름.static 멤버 형태로 적곤 했다.
하지만 다음과 같이 static import를 하면 컴파일러에게 다음 클래스의 static 멤버를 접근할 것이라고 알려줄 수 있기 때문에 클래스 이름을 생략해줄 수 있다.