본문 바로가기
Java/Java 예습

[Java] 자바의 객체 Part.2 예습_5

by 박채니 2022. 1. 26.

안녕하세요, 코린이의 코딩 학습기 채니입니다.

Java 객체를 예습했던 내용을 정리한 포스팅입니다.

 

다형성(Polymorphism)

: 객체지향 프로그래밍의 3대 특징 중 하나'여러 개의 형태를 갖는다'는 의미

: 하나의 행동으로 여러 가지 일을 수행하는 개념 (다형성 + 오버라이딩 개념이 결합 되었을 때)

: 상속을 이용한 기술로 부모 타입으로부터 파생된 여러 가지 타입의 자식 객체를 부모 클래스 타입 하나로 다룰 수 있는 기술

 

클래스 형변환

업 캐스팅 (Up Casting)

: 상속 관계에 있는 부모, 자식 클래스 간에 부모타입의 참조형 변수가 모든 자식 타입의 객체 주소를 받을 수 있음

: 부모 자료형으로 자식 자료형을 다룰 수 있다.

 

다운 캐스팅 (Down Casting)

: 자식 객체의 주소를 받은 부모 참조형 변수를 가지고 자식의 멤버를 참조해야 할 경우, 

: 부모 클래스 타입의 참조형 변수를 자식 클래스 타입으로 형 변환하는 것

: 자동으로 처리 되지 않기 때문에 반드시 후손 타입 명시해서 형 변환

 

instanceof 연산자

: 현재 참조형 변수가 어떤 클래스 형의 객체 주소를 참조하고 있는 지 확인 할 때 사용

: 클래스 타입이 맞으면 true, 맞지 않으면 false 반환

 

// 부모 클래스
package com.kh.p3.poly.model.vo;

public class Hobby {
	private int spendTime;	//투자 시간 (년)
	private int spendMoney;	//투자 금액 (만원)
	
	public Hobby() {
	}
	
	public Hobby (int spendTime, int spendMoney) {
		this.spendTime = spendTime;
		this.spendMoney = spendMoney;
	}
	
	@Override
	public String toString() {
		return "이 취미를 위해 투자한 시간은 " + spendTime + "년, 투자한 금액은 " + spendMoney + "만원이다."; 
	}
	
	public void print() {
		System.out.println("이 취미를 위해 투자한 시간은 " + spendTime + "년, 투자한 금액은 " + spendMoney + "만원이다.");
	}
}
// 자식 클래스

package com.kh.p3.poly.model.vo;

public class Collecting extends Hobby {
	private String stuff;	//수집 물품
	
	public Collecting() {
	}
	
	public Collecting(String stuff) {
		this.stuff = stuff;
	}
	
	public Collecting(int spendTime, int spendMoney, String stuff) {
		super(spendTime, spendMoney);
		this.stuff = stuff;
	}
	
	public void colMethod() {
		System.out.println(super.toString() + "내가 취미로 모으는 물품은 " + stuff + "이다.");
	}
	
	@Override 
	public void print() {
		System.out.println(super.toString() + "내가 취미로 모으는 물품은 " + stuff + "이다.");
	}
	
}
// 자식 클래스

package com.kh.p3.poly.model.vo;

public class ReadingBook extends Hobby {
	private int bookNo;	//읽은 책의 수(권)
	
	public ReadingBook() {	
	}
	
	public ReadingBook(int bookNo) {
		super();
		this.bookNo = bookNo;
	}
	
	public ReadingBook(int spendTime, int spendMoney, int bookNo) {
		super(spendTime, spendMoney);
		this.bookNo = bookNo;
	}
	
	public int getBookNo() {
		return bookNo;
	}
	
	public void setBookNo(int bookNo) {
		this.bookNo = bookNo;
	}
	
	public void reMethod() {
		System.out.println(super.toString() + "내가 한 달에 읽는 책은 " + bookNo + "(권)이다.");
	}
	
	@Override
	public void print() {
		System.out.println(super.toString() + "내가 한 달에 읽는 책은 " + bookNo + "(권)이다.");
	}
	
	
}
@run
package com.kh.p3.poly.run;

import com.kh.p3.poly.model.vo.Collecting;
import com.kh.p3.poly.model.vo.Hobby;
import com.kh.p3.poly.model.vo.ReadingBook;

public class Run {

	public static void main(String[] args) {
		Hobby h = new Hobby();
		Hobby upH = (Hobby)(new Collecting());	//업 캐스팅 (Hobby)가 없어도 자동으로 업 캐스팅 됨
		// Hobby upH = new Collecting();  로도 가능
		//ReadingBook downRb = (ReadingBook)(upH);	
        	//다운 캐스팅(주의 : 부모 클래스가 표현하고 있는 자식 클래스자료형으로 해야 함)
		
		// 다형성 적용
		Hobby polyH = new Collecting();
		Hobby polyH1 = new Collecting(3, 100, "우표");
		Hobby polyRb1 = new ReadingBook(4, 200, 100);
		Hobby polyRb2 = new ReadingBook(5, 300, 200);
		Hobby polyH2 = new Collecting(6, 400, "도자기");
		
		// 다형성 + 배열
		Hobby[] polyArr = new Hobby[4];
		polyArr[0] = new Collecting(3, 100, "우표");
		polyArr[1] = new ReadingBook(4, 200, 100);
		polyArr[2] = new ReadingBook(5, 300, 200);
     	   	polyArr[3] = new Collecting(6, 400, "도자기");
	}
}

다형성의 특성과 배열을 이용하여 보다 간편하게 표현할 수 있다.

 

객체배열과 다형성

: 다형성을 이용하여 상속 관계에 있는 하나의 부모 클래스 타입의 배열 공간에 여러 종류의 자식 클래스 객체 저장 가능

 

		// 다형성 적용
		Hobby polyH = new Collecting();
		Hobby polyH1 = new Collecting(3, 100, "우표");
		Hobby polyRb1 = new ReadingBook(4, 200, 100);
		Hobby polyRb2 = new ReadingBook(5, 300, 200);
		Hobby polyH2 = new Collecting(6, 400, "도자기");
		
		// 다형성 + 배열
		Hobby[] polyArr = new Hobby[4];
		polyArr[0] = new Collecting(3, 100, "우표");
		polyArr[1] = new ReadingBook(4, 200, 100);
		polyArr[2] = new ReadingBook(5, 300, 200);
		polyArr[3] = new Collecting(6, 400, "도자기");
		
		
		((Collecting)polyArr[0]).colMethod();
		((ReadingBook)polyArr[1]).reMethod();
		((ReadingBook)polyArr[2]).reMethod();
		((Collecting)polyArr[3]).colMethod();
		
		//for문 사용(instanceOf + if문 사용)
		for(int i = 0; i < polyArr.length; i++) {
			if(polyArr[i] instanceof Collecting) {
				((Collecting)polyArr[i]).colMethod();
			} else {
				((ReadingBook)polyArr[i]).reMethod();
			}
		}

 

이와 같이 for문 (instanceof +if문)을 사용하여 코드를 단순화 시킬 수 있음

 

매개변수와 다형성

: 다형성을 이용하여 메소드 호출 시 부모타입의 변수 하나만 사용해 자식 타입의 객체를 받을 수 있음

 

바인딩

: 실제 실행할 메소드 코드와 호출하는 코드를 연결 시키는 것

: 프로그램이 실행되기 전에 컴파일이 되면서 모든 메소드는 정적 바인딩 

동적 바인딩

: 컴파일 시 정적 바인딩된 메소드를 실행할 당시의 객체 타입을 기준으로 바인딩 되는 것

동적 바인딩 성립 요건

: 상속 관계로 이루어져 다형성이 적용된 경우,

: 메소드 오버라이딩이 되어 있으면 정적으로 바인딩 된 메소드 코드보다 오버라이딩 된 메소드 코드를 우선적으로 수행

 

@run

        	Hobby[] polyArr = new Hobby[4];
		polyArr[0] = new Collecting(3, 100, "우표");
		polyArr[1] = new ReadingBook(4, 200, 100);
		polyArr[2] = new ReadingBook(5, 300, 200);
		polyArr[3] = new Collecting(6, 400, "도자기");

// 동적 바인딩 적용 (오버라이딩 적용)
		for(int i = 0; i < polyArr.length; i++) {
			polyArr[i].print();
		}
        
@출력값
이 취미를 위해 투자한 시간은 3년, 투자한 금액은 100만원이다.내가 취미로 모으는 물품은 우표이다.
이 취미를 위해 투자한 시간은 4년, 투자한 금액은 200만원이다.내가 한 달에 읽는 책은 100(권)이다.
이 취미를 위해 투자한 시간은 5년, 투자한 금액은 300만원이다.내가 한 달에 읽는 책은 200(권)이다.
이 취미를 위해 투자한 시간은 6년, 투자한 금액은 400만원이다.내가 취미로 모으는 물품은 도자기이다.

Hobby class(부모 클래스)에 있는 print 메소드를 실행하지 않고,

자식 클래스에 있는 override된 print메소드가 먼저 실행되면서 부모 클래스에 있는 print메소드는 무시!!

 

이와 같이 활용하여 복잡했던 코드들을 간편하게 단순화 시킬 수 있음