중첩 클래스, 익명객체

2019. 3. 12. 20:01JAVA

--------------------------------중첩클래스----------------------------------


중첩클래스의 목적

특정 클래스 안에서만 사용되는 클래스의 경우 어차피 특정 클래스만 사용할 것이라

특정 클래스안에 만든다.


중첩클래스는 대부분 interface가 있다.





중첩 클래스는 몇가지 종류가 있다.


1. 멤버 내부클래스


public class A{

// 멤버내부 클래스

public class B {


}

}




2. 정적 내부클래스


public class A{

//정적내부 클래스

public static class B{


}

}



3. 로컬 내부클래스


public class A{

//로컬내부 클래스

class B{


}

}



// 컴파일 예시---------------------------------

public class Outter{

public class Inner{

}

}


이렇게 내부 클래스를 컴파일할경우 파일이 폴더에


Outter$Inner.class // 내부클래스 클래스파일

Outter.class

Outter.java 

이렇게 만들어진다.





---------예시----------------------------------

public class Outter{

// 인스턴스 내부 클래스

// Outter 객체가 생성된 다음에만 사용할 수 있는 내부 클래스

// Outter 객체의 모든 멤버(필드, 메소드)를 사용할 수있다.

public class Inner{

}


// 정적 멤버 클래스

// Outterr객체 생성없이 사용할 수 있는 내부 클래스

// Outter의 정적 멤버(정적필드, 정적 메소드)만 사용할 수 있다.

public static class Inner2 {

}

public void method(){

// 로컬 내부클래스

// 메소드가 실행되는 동안에만 사용할 수 있는 내부 클래스

// Outter객체의 모든 멤버를 사용할 수 있다.

// 스택구조로 인해 로컬 내부 클래스가 포함된 메소드는 변수가 final처럼 사용해햐 한다.(final 이 안보이지만 있는것) 

class Inner3{

}

}

}












인스턴스 내부 클래스 예시-------------------------------------------

예시1)---------------------------------------------------


public class List {

int[] data = {10, 20, 30, 40, 50};


public Iterator getIterator(){

Iterator it = new ListIterator();

return it;

}


class ListIterator implements Iterator{

int[] clone;

int position = 0;


public ListIterator(){

clone = data;

position = 0;

}

public int next() {

int number = 0;

number = clone[position];

position++;


return number;

}


public boolean empty(){

if(position < clone.length){

return false;

} else{

return true;

}

}

}

}

//리스트 빼고 비었는지 확인하는것

예시2)--------------------------------------------------

public class IteratorApp{

public static void main(String[] args){

List list = new List();

Iterator iterator = list.getIterator();


System.out.println(iterator.empty());

System.out.println(iterator.next());

System.out.println(iterator.empty());

System.out.println(iterator.next());

System.out.println(iterator.empty());

System.out.println(iterator.next());

System.out.println(iterator.empty());

System.out.println(iterator.next());

System.out.println(iterator.empty());

System.out.println(iterator.next());


System.out.println(iterator.empty());

}

}



---------- 실행 ----------

false

10

false

20

false

30

false

40

false

50

true


출력 완료 (0초 경과) - 정상 종료





정적 멤버 클래스 예시----------------------------------------------------


예시 1)-------------------------------------------------------

public class Account {

private int no;

private String name;

private int balance;


public int getNo(){

return no;

}

public void setNo(int no){

this.no = no;

}

public String getName(){

return name;

}

public void setName(String name){

this.name = name;

}

public int getBalance(){

return balance;

}

public void setBalace(int balance){

this.balance = balance;

}


public static class AccountBuilder{

private int no;

private String name;

private int balance;


public  AccountBuilder no(int no){

this.no = no;

return this; // 메소드 체이닝

}

public AccountBuilder name(String name){

this.name = name;

return this;

}

public AccountBuilder balance(int balance){

this.balance = balance;

return this;

}

public Account build(){

Account account = new Account();

account.no = no;

account.name = name;

account.balance = balance;

return account;

}

}

}

예시 2)----------------------------------------------------

public class AccountApp{

public static void main(String[] args){

Account.AccountBuilder builder = new Account.AccountBuilder(); // 정적이라 클래스이름 . 클래스를 쓴것임

builder.no(10).name("홍길동");

Account account = builder.build();

System.out.println("번호 : "+account.getNo());

System.out.println("이름 : "+account.getName());

System.out.println("잔액 : "+account.getBalance());


builder.no(20).balance(100000);

Account account2 = builder.build();

System.out.println("번호 : "+account2.getNo());

System.out.println("이름 : "+account2.getName());

System.out.println("잔액 : "+account2.getBalance());


builder.no(40).name("김유신").balance(100000);

Account account3 = builder.build();

System.out.println("번호 : "+account3.getNo());

System.out.println("이름 : "+account3.getName());

System.out.println("잔액 : "+account3.getBalance());


Account account4 = builder.no(50).name("김가가").balance(100000000).build();

System.out.println("번호 : "+account4.getNo());

System.out.println("이름 : "+account4.getName());

System.out.println("잔액 : "+account4.getBalance());

}

}







-----------------------------------익명 객체---------------------------------------------


익명객체란

추상 클래스나 인터페이스의 메소드를 객체 생성 시점 즉시에 구현한 객체.

보통 GUI프로그램을 만들때 많이 쓴다. 이유는 UI프로그램은 한곳에서만 실행되는 클래스를 만드는경우가 많은데

그때마다 클래스를 만들면 낭비라 익명객체를 만든다. (클래스파일의 낭비를 줄임)



(예시1)------------------------------------------------

public interface Pen{

void draw()'

}


이후 객체생성시

Pen pen = new Pen(); // 에러 interface라 객체가 생성이안되지만

메소드가 구현이 안돼서 생성이안되는데




Pen pen = new Pen(){

public void draw(){

System.out.println("빨갛게");

}

} // 이렇게 객체 생성시 메소드를 구현하면 생성이된다