본문 바로가기
Develope_Web&App

[Java ] 내부 클래스

by 스타트업_디벨로퍼 2021. 2. 2.

내부 클래스는 마치 변수를 선언하는 것과 같은 위치에 선언할 수 있으며, 변수의 선언위치에 따라 인스턴스변수, 클래스 변수(static 변수), 지역 변수로 구분되는 것과 같이 내부 클래스도 선언위치에 따라 구분되어짐.

 

인스턴스 클래스 : 외부 클래스의 멤버변수 선언위치에 선언하며, 외부 클래스의 인스턴스멤버처럼 다루어진다. 주로 외부 클래스의 인스턴스 멤버들과 관련된 작업에 사용될 목적으로 선언된다.

 

스태틱 클래스 : 외부 클래스의 멤버변수 선언위치에  선언하며, 외부 클래스의 static 멤버처럼 다루어진다. 주로 외부 클래스의 static 멤버, 특히 static 메서드에서 사용될 목적으로 선언된다.

 

지역 클래스 : 외부 클래스의 메서드나 초기화블럭 안에 선언하며, 선언된 영역 내부에서만 사용될 수 있다.

 

익명 클래스 : 클래스의 선언과 객체의 생성을 동시에 하는 이름없는 클래스

 

 

내부 클래스의 선언 -> 인스턴스 변수, 클래스 변수, 지역변수처럼 클래스도 유사하게 나눌 수 있다.

class Outer {
	class InstanceInner { }
    static class StaticInner {}
    
    void myMethod(){}
    	class LocalInner {}

	}
}

내부 클래스에서도 멤버처럼 동일하게 지정할 수 있다.

 

class Outer { 
	private int iv = 0;
    protected static int cv = 0;
    
    void myMethod() {
    	int lv = 0;
	}

}
class Outer {
	private class InstanceInner {}
    protected static class StaticInner{}
    
    void myMethod(){
		class LocalInner {}    
    }
}

 

 

이 경우에서는 AAA

package Main;

class AAA{
	int i = 100;
	BBB b = new BBB();
	class BBB{
		void method() {
			AAA a = new AAA();
			System.out.println(a.i);
            System.out.println(i);//내부라서 i도 바로 불러올수도 있음
 
            
		}
		
	}

}

class CCC{
	BBB b = new BBB(); // 에러
}

public class InnerTest {

	public static void main(String[] args) {
		// TODO Auto-generated method stub
		 BBB b = new BBB(); //AAA 객체 생성후 만들어야함
		 b.method();
	}

}

 

 

 

일반적인 class는 default / public 만 되나

 

내부 클래스는 default/ public / private / protected 모두 가능하다!! 

 

 

class InnerEx1 {

	class InstanceInner {
		int iv = 100;
		static int cv= 100; //에러! static 변수를 선언할 수 없다.
		final static int CONST = 100; // final static 은 상수이므로 허용
	}
	
	static class StaticInner {
		int iv = 200;
		static int cv= 200; //static 클래스만 static 멤버를 정의할 수 잆다.
		final static int CONST = 100;
	}
	
	void myMethod() {
		class LocalInner {
			int iv = 300;
			static int cv = 300; //에러! static 변수를 선언할 수 없다.
			final static int CONST = 300; //final static은 상수이므로 허용
		}
	}
	
	public static void main(String args[]) {
		
		System.out.println(InstanceInner.CONST);
		System.out.println(StaticInner.cv);
	}
}

 

 

package Main;

class InnerEx2 {
	class InstanceInner {}
	
	static class StaticInner {}
	// 인스턴스 멤버 간에는 서로 직접 접근이 가능하다.
	InstanceInner iv = new InstanceInner();
	
	//static 멤버 간에는 서로 직접 접근이 가능하다.
	static StaticInner cv = new StaticInner();
	
	// static 멤버가 instance 멤버에 대한 접근 은 불가하다
	
	static void staticMethod() {
		//static 멤버는 인스턴스멤버에 직접 접근할 수 없다.
		//InstanceInner obj1 = new InstanceInner();
		StaticInner obj2 = new StaticInner();
		
		
		//굳이 접근하려면 아래와 같이 객체를  생성해야 한다.
		// 인스턴스클래스는 외부 클래스를 먼저 생성해야만 생성할 수 있다.
		//InnerEx2 outer = new InnerEx2();
		//InstanceInner obj1 = outer.new InstanceInner();
	}
	
	void instanceMethod() {
		// 인스턴스메서드에서는 인스턴스멤버와 static 멤버 모두 접근가능하다.
		InstanceInner obj1 = new InstanceInner();
		StaticInner obj2 = new StaticInner();
		// 메서드 내에 지역적으로 선언된 내부 클래스는 외부에서 접근할 수 없다.
		//LocalInner lv = new LocalInner();
	}
	
	void myMethod() {
		class LocalInner {}
		LocalInner lv = new LocalInner();
	}
}
package Main;

public class InnerEx3 {
	private int outerIv = 0;
	static int outerCv = 0;
	
	class InstanceInner {
		int iiv = outerIv; //외부 클래스의 private멤버도 접근가능하다.
		int iiv2 = outerCv;
	}
	
	static class StaticInner { 
		//int siv = outerIv; // 스태틱 클래스는 외부 클래스의 인스턴스멤버에 접근할 수 없다.
		static int scv = outerCv;
	}
	
	void myMethod() {
		int lv = 0; //지역변수 <- 메서드종료와 함께 소멸, 1.8부터는 값 안바뀌면 상수로 간주! 
		final int LV = 0; //JDK1.8부터 final 생략 가능
		
		class LocalInner{
			int liv = outerIv; //<- 내부 클래스의 객체가 지역변수보다 더 오래 존재 가능! 
			int liv2 = outerCv;
			// 외부 클래스의 지역변수는 final이 붙은 변수만 접근간읗다.
			//int liv3 = lv;
			int liv4 = LV;
		}
	}
	public static void main(String[] args) {
		// TODO Auto-generated method stub

	}

}

 

 

익명 클래스

 

import java.awt.*;
import java.awt.event.*;

public class InnerEx8 {

	public static void main(String[] args) {
		// TODO Auto-generated method stub
		Button b = new Button("Start");
		b.addActionListener(new ActionListener() {
			public void actionPerformed (ActionEvent e) {
				System.out.println("ActionEvent Occured!!!");
			}
		}
		);
	}

}

 

반응형

'Develope_Web&amp;App' 카테고리의 다른 글

[Java의 정석] 객체지향 1-2  (0) 2021.02.03