-
Java | Inheritance 상속 & Overriding & Class 관계JAVA/JAVA 2020. 1. 29. 19:27
Inheritance 상속 개요
객체 지향 프로그래밍의 중요한 특징 중 하나
일반적으로 무언가를 물려받는다는 의미- 자식 클래스가 부모 클래스의 멤버 변수와 메소드를 물려받는 것
→ B 클래스가 A 클래스를 상속받으면 B 클래스는 A 클래스의 멤버 변수와 메소드 사용 가능 - 객체 지향 프로그램의 기반이 되는 기술
- 복사와 유사
※ 자바에서 클래스 작성시, 기본적으로 java.lang.Object 클래스를 상속받게 되어있음
형식
class 자식 클래스 extends 부모 클래스
※ 자식 클래스는 sub class, 부모 클래스는 super class 라고 함
장점
- 부모 클래스의 멤버변수와 메소드를 그대로 사용하기 때문에 재사용성이 높음
- 코드의 양을 줄이고 개발시간을 단축할 수 있음
단점
부모 클래스로부터 물려받은 메소드를 자식 클래스에서 그대로 사용하게 되기 때문에
자식 클래스의 내용에 맞지 않게 메소드가 동작하는 경우가 발생
특징
- 생성자는 상속 불가
구조적인 문제 때문에 그런데 이에 대해서는 나중에 다룰 예정 - private으로 선언된 멤버변수와 메소드는 상속 불가
접근제어자 private은 멤버변수와 메소드가 해당 클래스 내에서만 사용 가능하도록 함 - 다중 상속 불가, 동시에 여러 부모로부터 상속을 받을 수는 없음
프로그램이 복잡해지기 때문에 다중 상속을 제한함, 단일 상속만 가능
class 자식 extends 부모1, 부모2 (X)
class 자식 extends 부모1, calss 자식 extends 부모2 (O) - 누적 상속 가능
A클래스를 상속받는 B클래스를 C클래스가 상속받을 수 있음
멤버 변수와 메소드 개수가 증가하며 기능이 많아짐
Overriding 메소드 재정의
자바에서 다형성을 지원하는 방법 중 하나
부모 클래스로부터 상속받은 메소드를 같은 이름으로 재정의하는 것을 말함
상속의 단점을 보완할 수 있는 기법
사용례에서 상속과 함께 사용법을 다룸
Class 관계
has-a 관계
"A는 B를 가지고 있다"의 관계가 성립되는 포함 관계
철수가 지갑을 가지고 있다. (O)
지갑이 철수를 가지고 있다. (X)
→ 위와 같은 관계를 has-a 관계라고 함- A 클래스에서 B 클래스를 상속받는 것이 아니라 내부에 인스턴스(객체)를 따로 생성하는 것
→ 포함 관계, 인터페이스 사용시 필요한 관계 - 여러 클래스를 하나로 합쳐서 만들기 때문에 조각 프로그래밍에 용이
is-a 관계
"A는 B이다"의 관계가 성립되는 상속(extends) 관계
팀장은 그 회사의 직원이다.(O)
직원은 그 회사의 팀장이다.(X)
→ 위와 같은 관계를 is-a 관계라고 함- 상속을 사용하려면 반드시 논리적으로 is-a 관계가 성립되어야 함
- 부모클래스를 수정하면 자식클래스에 영향을 주지만 자식클래스를 수정해도 부모클래스에는 영향을 미치지 못함
- 자식클래스를 인스턴스(객체)로 생성하면 부모클래스의 멤버까지 포함한 인스턴스가 생성됨
사용례_상속 & Overriding & 객체 배열
예제 시나리오
신입 사원 → 부서배치(개발 1과)
팀장 → 개발 1과
급여: 연봉제 + 보너스(사원: 150%, 팀장: 300%)
Employee.java
package j200129; // 신입 사원 클래스 public class Employee { // 공통 멤버 변수 String name; int age; String gender; String addr; long salary; // 생성자 오버로딩 public Employee(){} public Employee(String name, int age, String gender, String addr, long salary) { this.name = name; this.age = age; this.gender = gender; this.addr = addr; this.salary = salary; } // 보너스를 반환하는 메소드, 사원 보너스: 150% double bonus() { return salary * 1.5; } // 저장되어 있는 값을 그대로 출력하는 메소드 void display() { System.out.println("===직원 정보==="); System.out.println("이름: " + name); System.out.println("나이: " + age); System.out.println("성별: " + gender); System.out.println("주소: " + addr); System.out.println("급여: " + salary); // 메소드 내부에서 동일 클래스 내의 일반 메소드 호출 System.out.println("보너스: " + bonus()); } public static void main(String[] args) { } }
※ Eclipse 생성자 자동 생성 : Source → Generate Constructor using Fields
Company.java
package j200129; // 팀장 이상 직원들의 정보를 저장할 클래스, Employee 클래스 상속 class Manager extends Employee { /* Employee 클래스로부터 상속 받은 멤버 변수 String name; int age; String gender; String addr; long salary; */ // Manager 클래스의 멤버 변수 String department; // 객체 배열 멤버 변수, 신입 사원들의 정보가 담긴 Employee 자료형 배열 Employee sub[]; // 생성자, 생성자는 상속받을 수 없기 때문에 직접 작성 해야 함 public Manager() {} public Manager(String name, int age, String gender, long salary, String addr, String department) { this.name = name; this.age = age; this.gender = gender; this.salary = salary; this.addr = addr; this.department = department; } // Employee 클래스의 bonus() 메소드 Overriding(재정의), ∵팀장 보너스: 300% double bonus() { return salary * 3.0; } } public class Company { public static void main(String[] args) { // 신입 사원 3명 채용 Employee e1 = new Employee("홍길동", 23, "남", "서울시 강북구", 1500); Employee e2 = new Employee("이순신", 25, "여", "경기도 광주시", 2100); Employee e3 = new Employee("강감찬", 22, "남", "대전시 중구", 1700); // 팀장 채용 Manager m1 = new Manager("이세종", 42, "남", 3000, "서울시 강남구", "개발 1과"); // 신입 사원 → 부서 배치, m1.sub 이라는 Employee객체 배열 생성 // Manager의 멤버 변수인 sub[] 객체 배열의 크기를 지정하고 초기화 m1.sub = new Employee[3]; m1.sub[0] = e1; m1.sub[1] = e2; m1.sub[2] = e3; // 사원 정보 출력, Employee를 상속받았기 때문에 Employee의 display() 메소드 사용 가능 System.out.println("====신입 사원===="); for (int i = 0; i < m1.sub.length; i++) { m1.sub[i].display(); } // 팀장 출력 System.out.println("====팀장===="); m1.display(); } }
결과
/* ====신입 사원==== ===직원 정보=== 이름: 홍길동 나이: 23 성별: 남 주소: 서울시 강북구 급여: 1500 보너스: 2250.0 ===직원 정보=== 이름: 이순신 나이: 25 성별: 여 주소: 경기도 광주시 급여: 2100 보너스: 3150.0 ===직원 정보=== 이름: 강감찬 나이: 22 성별: 남 주소: 대전시 중구 급여: 1700 보너스: 2550.0 ====팀장==== ===직원 정보=== 이름: 이세종 나이: 42 성별: 남 주소: 서울시 강남구 급여: 3000 보너스: 9000.0 */
상속과 오버라이딩(메소드 재정의), 클래스 관계에 대해 살펴보았습니다.
상속을 사용하면 클래스 간의 관계를 계층적으로 구조화할 수 있습니다.
가장 범위가 넓은 것에서부터 한 칸씩 내려가는 구조라고 이해하면 되겠습니다.(ex. 생물 → 동물 → 포유류 → 인간)
또한 오버라이딩을 사용하면 부모 클래스의 메소드를 재정의하여 사용할 수 있기 때문에
일일이 새롭게 메소드를 정의하지 않아도 돼서 재사용성 및 작업 편의성을 한층 높일 수 있습니다.
'JAVA > JAVA' 카테고리의 다른 글
Java | Super & 생성자 호출 메커니즘 (0) 2020.01.30 Java | 접근 제어자 with 상속 (0) 2020.01.30 Java | Array of Objects 객체 배열 (0) 2020.01.29 Java | 다차원 배열_이차원 배열 (0) 2020.01.29 Java | Ellipsis 가변인수 (0) 2020.01.29 - 자식 클래스가 부모 클래스의 멤버 변수와 메소드를 물려받는 것