자바에서는 클래스 내부에 또 다른 클래스를 정의할 수 있으며, 이렇게 정의된 클래스를 중첩 클래스(Nested Class)라고 부릅니다.
접근 제어자 사용 범위는 다음과 같습니다.
- 내부 클래스(Inner Class): private, public, protected, default 모두 사용 가능
- 외부 클래스(Outer Class): default 또는 public만 사용 가능
자바의 중첩 클래스는 크게 두 가지 유형으로 나뉩니다.
- 정적 중첩 클래스(Static Nested Class)
- 비정적 중첩 클래스(Non-Static Nested Class, 내부 클래스)
1. 정적 중첩 클래스(Static Nested Class)
- 내부 클래스를 static 키워드로 선언하면 이를 정적 중첩 클래스라고 합니다.
- static으로 선언되기 때문에 외부 클래스의 인스턴스와는 아무런 관계를 맺지 않습니다.
- 외부 클래스의 인스턴스 생성 없이도 독립적으로 사용할 수 있으며, 외부 클래스의 static 멤버에는 접근이 가능합니다.
예제 코드
class Car {
static class Wheel {
public void rotate() {
System.out.println("The wheel is rotating");
}
}
}
public class Test {
public static void main(String args[]) {
Car.Wheel wheel = new Car.Wheel();
wheel.rotate();
}
}실행 결과
The wheel is rotating
위 예제를 보면 Car.Wheel 객체를 생성할 때 외부 클래스인 Car의 인스턴스가 필요하지 않은 것을 확인할 수 있습니다. 이것이 정적 중첩 클래스의 가장 큰 특징입니다.
2. 비정적 중첩 클래스(Non-Static Nested Class)
- 비정적 중첩 클래스는 자바에서 흔히 말하는 내부 클래스(Inner Class)를 의미합니다.
- 내부 클래스는 외부 클래스의 객체(인스턴스)와 연결되어 있으며, 외부 클래스의 다른 변수나 메서드처럼 취급됩니다.
- 외부 클래스의 인스턴스에 종속되어 있기 때문에 내부 클래스 안에서는 static 변수를 선언할 수 없습니다.
예제 코드
public class OuterClassTest {
private int a = 10;
public void innerClassInstance() {
InnerClassTest inner = new InnerClassTest();
inner.outerObject();
}
public static void main(String args[]) {
OuterClassTest outer = new OuterClassTest();
outer.innerClassInstance();
}
class InnerClassTest {
public void outerObject() {
System.out.println("Outer Value of a is: " + a);
}
}
}실행 결과
Outer Value of a is: 10
위 예제에서 내부 클래스 InnerClassTest는 외부 클래스의 private 변수 a에 직접 접근하여 값을 출력합니다. 이처럼 비정적 내부 클래스는 외부 클래스의 모든 멤버(private 포함)에 자유롭게 접근할 수 있다는 장점이 있습니다.
정리
| 구분 | 정적 중첩 클래스 | 비정적 중첩 클래스(내부 클래스) |
|---|---|---|
| 선언 방식 | static 키워드 사용 | 키워드 없이 선언 |
| 외부 클래스 인스턴스와의 관계 | 독립적 (관계 없음) | 종속적 (객체와 연결) |
| 객체 생성 방법 | new Car.Wheel() | 외부 클래스 인스턴스를 통해 생성 |
| static 변수 선언 | 가능 | 불가능 |
두 클래스의 차이를 이해하면 상황에 맞게 적절한 중첩 클래스를 선택하여 코드의 응집도와 가독성을 높일 수 있습니다.