BackEnd/JAVA

JAVA inherit 상속, private, super 생성자

H_Develop 2022. 7. 28. 08:15

extends (상속)
상속(inherit) 부모가 보유하고 있는 재산 (필드:맴버 메서드와 맴버 변수) 중 일부/전부를 자식이 물려받는 것.

클래스 상속은 객체의 재사용이라는 장점 뿐 아니라, 
코드의 간결성을 제공해주는 객체지향 언어의 최고 장점이라 할 수 있다. 
그러므로 잘 정의된 부모 클래스가 있다면 자식 클래스의 작성이 간편해진다는 장점이 있다.

객체의 재사용코드의 간결함이 있다.

잘 정의 된 부모 클래스(슈퍼 클래스)의 필드들을 자식 클래스(서브 클래스)에서 불러다 사용한다.
하지만 부모 클래스에서 private로 선언된 맴버는 자식 클래스에서 사용할 수 없다.

OOP(Object Oriented Programming : 객체지향언어) 
 java, C++, ... 클래스를 사용해서 객체를 만들고 이 객체로 모든 현상을 설명하는 프로그래밍 기법
 Object가 최상위 객체이다.

 

 

상속 개념

 

class Parent {
	private int money = 200;
	private String str = "서울";
	public int getMoney() {
		return money;
	}
	public void setMoney(int money) {
		this.money = money; // parent class 의 money
	}
	public String getStr() {
		return str;
	}
	public void setStr(String str) {
		this.str = str;		// parent class 의 str
	}
}
class Child extends Parent {
	private String car = "Grandeur"; // 자식 클래스에서 변수 선언
	public String getCar() {		 // 자식 클래스에서 두개의 메서드 정의
		return car;
	}
	public void setCar(String car) {
		this.car = car;
	}
}
public class ex1 {
	public static void main(String[] args) {
		Child c1 = new Child();	// 인스턴스화 한다.
		System.out.println(c1.getCar()); 	// Child가 자신의 맴버 메서드를 사용
		System.out.println(c1.getMoney());	// Child가 Parent class의 메서드 사용
		if(c1 instanceof Parent) {	
			// instance == 객체, instanceof 타입은 boolean, c1은 Parent의 자식인지 체크
			// instanceof는 객체화 여부를 점검하는데, boolean으로 결과를 보인다.
			System.out.println("c1은 Parent의 자식이다.");
		}
		System.out.println("-----------------------");
	}
}

 

객체의 형변환

 

class Parent {
	private int money = 200;
	private String str = "서울";
	public int getMoney() {
		return money;
	}
	public void setMoney(int money) {
		this.money = money; // parent class 의 money
	}
	public String getStr() {
		return str;
	}
	public void setStr(String str) {
		this.str = str;		// parent class 의 str
	}
}

class Child extends Parent {
	private String car = "Grandeur"; // 자식 클래스에서 변수 선언
	public String getCar() {		 // 자식 클래스에서 두개의 메서드 정의
		return car;
	}
	public void setCar(String car) {
		this.car = car;
	}
}

public class ex1 {
	public static void main(String[] args) {
		Child c1 = new Child();	// 인스턴스화 한다.
		System.out.println(c1.getCar()); 	// Child가 자신의 맴버 메서드를 사용
		System.out.println(c1.getMoney());	// Child가 Parent class의 메서드 사용
		if(c1 instanceof Parent) {	
			// instance == 객체, instanceof 타입은 boolean, c1은 Parent의 자식인지 체크
			// instanceof는 객체화 여부를 점검하는데, boolean으로 결과를 보인다.
			System.out.println("c1은 Parent의 자식이다.");
		}
		System.out.println("-----------------------");
		Child ch = new Child();
		Parent pr = new Parent();
		pr = (Parent)ch;	// casting 형변환, 
		ch = (Child)pr;		// 자식을 부모/부모를 자식에게 형변환 함.
// 부모를 자식에 대입함으로써 자식은 자신의 모든 필드와 부모의 모든 필드를 사용할 수 있음.
// 클래스 캐스팅은 많이 사용하지 않는다.		
		System.out.println(ch.getCar());	// 자식이 자식 맴버 사용
		System.out.println(ch.getMoney());	// 자식이 부모 맴버 사용
		System.out.println(ch.getStr());	// 자식이 부모 맴버 사용
		System.out.println(pr instanceof Child);
		pr = ch; 
// 자식을 부모에게 대입, 자식을 부모에게 대입해도 부모는 자신의 맴버들만 사용할 수 있다.
		System.out.println(pr.getMoney()); // 부모는 자신의 맴버만 사용가능
		System.out.println(pr.getStr());
//		System.out.println(pr.getCar()); // 부모가 자식 맴버 사용 불가
//		System.out.println((Child)pr.getCar()); // 부모를 형변환 하더라도 자식 맴버 사용 불가
	}
}

 

 

매개변수 없는 메서드 사용

 

class Animal {	
	int leg;		// 동물의 공통적인 부분은 부모 클래스에서 변수와 매서드를 정리.
	String shout;
	
	public int getLeg() {
		return -1;
	}
	public String getShout() {
		return shout;
	}
	public void setShout(String shout) {
		this.shout = shout;
	}
}

class Duck extends Animal {	// 모든 동물에 속하지 않는 날개 같은 경우, 자식 클래서에서 따로 정의
	private String wing = "날개가 있어요";
	public String getWing() {
		return wing;
	}
	public int getLeg() {
		System.out.println("Duck의 메서드 오버라이딩");
		return leg;
	}
}

class Ant extends Animal {
	private String legs = "다리가 많아요";
	public String getLegs() {
		return legs;
	}
	public int getLeg() {	// 부모의 getLeg() 메서드를 가져와서 다음처럼 print 하는 메서드 오버라이딩
		System.out.println("Ant의 메서드 오버라이딩 ");
		return leg;		// overriding을 따로 하지않으면, 부모클래스 getLeg()의 return값, -1이 반환된다.
// 부모의 매서드를 오버라이딩 했기에 return 값으로 Ant class의 legs를 사용할 수 없고,
// Animal class 의 leg를 사용해야 한다.
	}
}

public class ex2 {
	public static void main(String[] args) {
		Duck duck = new Duck();
		System.out.println("날개 : " + duck.getWing());
		duck.leg = 2;
		System.out.println("다리 : " + duck.getLeg());
		duck.setShout("꽥꽥");
		System.out.println("울음소리 : " + duck.getShout());
		
		Ant ant = new Ant();
		System.out.println("날개 : " + ant.getLegs());
		ant.leg = 8;
		System.out.println("다리 : " + ant.getLeg());
		ant.setShout("슥..슥..");
		System.out.println("울음소리 : " + ant.getShout());
	}
}

 


private 
변수, 메서드는 다른 오브젝트에서 사용할 수 없고, 서브 클래스로 상속될 수 없다.

 

class Person {
//	private String name;
	String name;
	
	void setName(String n) {
		this.name = n;
	}
	String getName() {
		return name;
	}
}
class Girl extends Person {
	void print() {
		System.out.println(getName() + " 양");
	}
}
public class ex1 {
	public static void main(String[] args) {
		Girl nara = new Girl();
		nara.setName("나라");		// 부모 메서드 호출하여 사용
		nara.name = "나라";
		// 바로 접근, Person class 에서 private로 변수를 생성했으면 변경불가.
		
		nara.print();
	}
}

 

super, 생성자

 

class Parent {
	public Parent(int n) {	
		// Class와 동일한 이름으로 Method 생성 == 생성자(Construct : C프로그램에서 구조체)
		// Class c = new Class(); 에서 뒤에 Class()가 생성자 호출한다는 의미이다.
		// instance화 할 때, 제일 먼저 호출되어 실행되는 일종의 메서드이다.
		// 생성자는 instance 필드 값들을 초기화 시킨다.
		// public class_name(parameter) {...} 구문.
		System.out.println("부모 클래스 " + n);
	}
}
class Child extends Parent {
	public Child() {	// 생성자 메서드
		super(1);		// 부모 클래스 parent 생성자 호출
		System.out.println("자식 클래스 ");
	}
}
public class ex1 {
	public static void main(String[] args) {
		Child ch = new Child();
		new Child();
// 자식 클래스에서 객체를 생성하면, 자식의 생성자가 호출되지만 먼저 super()로 부모의 생성자를 호출했기에,
// 부모 클래스의 생성자에 접근하게 된다.
	}
}

부모 클래스 1
자식 클래스 
부모 클래스 1
자식 클래스 

객체 생성으로도 생성자를 호출한다.

 

 

자식 클래스에서 오버라이딩 된 부모 매서드 까지 호출

 

class Animalss {
	String name;
	int age;
	void printPet() {
		System.out.println("이름 : " + name );
		System.out.println("나이 : " + age);
	}
}
class Cat extends Animalss {
	String variety;
	@Override
	void printPet() {
		super.printPet();	// 객체 생성 없이, 부모 메서드 호출
		System.out.println("종류 : " + variety); // 자신의 변수로 부모의 메서드를 호출
	}
}
public class ex1 {
	public static void main(String[] args) {
		Cat cat = new Cat();
		cat.name = "양순이";
		cat.age = 5;
		cat.variety = "페르시안";
		cat.printPet();
	}
}

 

이름 : 양순이
나이 : 5
종류 : 페르시안