늦은 프로그래밍 이야기
객체지향 (2) 상속, 접근제어자 본문
상속 (Inheritance)
- 기존의 클래스를 재사용하는 방식
- 이미 설계된 클래스를 바탕으로 새로운 클래스를 만들 수 있다.
- 상속을 통해 클래스 간 계층구조를 만든다.(슈퍼클래스, 서브클래스)

특징
1) 부모클래스(슈퍼클래스)에서 정의된 필드와 메소드를 물려 받는다.
2) 새로운 필드와 메소드를 추가할 수 있다. (오버로딩)
3) 부모클래스(슈퍼클래스)에서 물려받은 메소드를 수정할 수 있다. (오버라이딩)
클래스 확장
자식클래스(서브클래스) 선언하기
- 부모클래스(슈퍼클래스)를 확장하여 자식클래스(서브클래스)를 선언할 수 있다.
class 서브클래스명 extends 슈퍼클래스명 {
서브클래스에 추가하는 멤버
...
서브클래스의 생성자(인수목록) {
...
}
서브클래스에 추가하는 메소드(인수목록) {
...
}
}
자식클래스(서브클래스)의 객체 생성
- 객체를 생성하는 방법은 클래스의 객체를 생성하는 방법과 동일하다.
클래스명 변수명 = new 클래스명(인수);
예시
class Dog extends Animal {
Dog(String name) {
this.name = name;
}
public void cry() {
System.out.println(name + " is barking!");
}
}
public class Main {
public static void main(String[] args) {
Animal dog = new Dog("코코");
dog.cry();
}
}
- 부모클래스 Animal을 상속받은 자식클래스 Dog를 선언한다.
부모클래스의 생성자 지정
- 자식클래스의 생성자에서 부모클래스의 생성자를 호출하고 싶은 경우 super()를 사용한다.
super(name, color);
오버로딩 (Overloading)
- 한 클래스 내의 동일한 이름의 메소드를 여러개 정의하는 것.
- 기존에 없는 새로운 메소드를 정의하는 것.
조건
1) 메소드의 이름이 동일해야 한다.
2) 매개변수의 개수 혹은 타입이 달라야 한다.
예시
- 오버로딩이 아닌 경우
int add(int x, int y, int z) {
int result = x + y + z;
return result;
}
long add(int a, int b, int c) {
long result = a + b + c;
return result;
}
- 반환 타입은 다르지만 매개변수의 자료형과 갯수가 같으므로 오버로딩이 아니다.
- 오버로딩인 경우
int add(int x, int y, int z) {
int result = x + y + z;
return result;
}
long add(int a, int b, long c) {
long result = a + b + c;
return result;
}
int add(int a, int b) {
int result = a + b;
return result;
}
- 첫번째와 두번째는 매개변수의 다입이 다르고, 세번째는 개수가 다르다.
오버라이딩 (Overriding)
- 부모클래스로부터 상속받은 메소드의 내용을 변경하는 것.
조건
1) 부모클래스의 메소드와 이름이 같아야 한다.
2) 부모클래스의 메소드와 매개변수가 같아야 한다.
3) 부모클래스의 메소드와 반환타입이 같아야 한다.
예시
class Animal {
String name;
String color;
public void cry() {
System.out.println(name + " is crying.");
}
}
class Dog extends Animal {
Dog(String name) {
this.name = name;
}
@Override
public void cry() {
System.out.println(name + " is barking!");
}
}
public class Main {
public static void main(String[] args) {
Animal dog = new Dog("코코");
dog.cry();
}
}
// 자식클래스에서 override한 cry메소드의 문장이 출력된다.
- 부모클래스인 Animal에 있는 cry 메소드와 메소드의 이름, 매개변수, 반환타입이 같고 메소드 내부의 반환문장이 바뀌었다.
접근제어자 (Access modifier)
- 접근제어자 : 멤버 변수/함수 혹은 클래스에 사용되며 외부에서의 접근을 제한하는 역할을 한다.
- 클래스 내부에 선언된 데이터를 부적절한 사용으로부터 보호.
- 캡슐화(encapsulation)
종류
1) private : 같은 클래스 내에서만 접근이 가능
2) default(nothing) : 같은 패키지 내에서만 접근이 가능
3) protected : 같은 패키지 내에서, 그리고 다른 패키지의 자손클래스에서 접근이 가능
4) public : 접근 제한이 전혀 없음.
예시
ModifierTest.java (패키지)
package pkg;
public class ModifierTest {
private void messageInside() { // private 같은 클래스 이외는 호출불가
System.out.println("This is private modifier");
}
public void messageOutside() { // public 접근제한 없음.
System.out.println("This is public modifier");
messageInside(); // 같은 클래스 내여서 호출 가능.
}
protected void messageProtected() { // protected 같은 패키지, 다른패키지의 자손클래스만 호출가능
System.out.println("This is protected modifier");
}
void messagePackagePrivate() { // default 같은 패키지 내에서만 호출가능
System.out.println("This is package private modifier");
}
}
Main.java
import pkg.ModifierTest;
class Child extends ModifierTest {
void callParentProtectedMember() {
System.out.println("Call my parent's protected method");
super.messageProtected(); // 다른 패키지의 자손클래스이기 때문에 protected 호출가능.
}
}
public class Main {
public static void main(String[] args) {
ModifierTest modifierTest = new ModifierTest();
modifierTest.messageOutside(); // public이기 때문헤 호출가능.
// modifierTest.messageInside(); // compile error
// modifierTest.messageProtected(); // compile error
Child child = new Child();
child.callParentProtectedMember();
}
}
'내일배움캠프 > Java 기초' 카테고리의 다른 글
| 컬렉션, 제네릭스 (0) | 2022.11.16 |
|---|---|
| 객체지향 (3) 추상클래스, 인터페이스 (0) | 2022.11.16 |
| 객체지향 (1) 클래스, 인스턴스, 메소드, 생성자 (0) | 2022.11.15 |
| 자주 발생하는 에러, 해결방법 (0) | 2022.11.14 |
| 조건문, 반복문 (0) | 2022.11.14 |