코드스테이츠 14일차

안형준·2022년 5월 13일
0

코드스테이츠

목록 보기
14/32
post-thumbnail

1차 학습목표

  1. 자바 객체지향 프로그래밍의 핵심 개념과 원리를 이해할 수 있다.
  2. 자바 상속의 핵심개념을 이해하고 포함 관계와의 차이를 구별할 수 있다.
  3. 자바 캡슐화를 구현하기 위한 수단으로 접근 제어자와 getter/setter 메서드를 이해하고 활용할 수 있다.
  4. 다형성을 위한 참조변수의 형변환을 이해하고, 코드 예제를 통해 다형성의 핵심 내용과 효과를 이해하고 활용할 수 있다.
  5. 추상 클래스와 인터페이스를 통해 추상화가 어떻게 실현될 수 있는 지 이해하고 이를 활용할 수 있다.
👻다형성
다형성이란 하나의 객체가 여러 가지 형태를 가질 수 있는 것을 의미한다.
자바에서 다형성은 한 타입의 참조변수를 통해 여러 타입의 객체를 참조할 수 있도록 만든 것을 의미한다.(상위 클래스 타입의 참조변수를 통해서 하위 클래스의 객체를 참조할 수 있도록 허용한 것)
하지만 그 반대인 하위 클래스의 타입으로 상위 클래스 객체를 참조하는 것은 불가능하다.
그 이유는 상위 클래스의 멤버 갯수보다 하위 클래스의 것이 더 많기 때문이다.

그렇다면 다형성을 사용할 수 있어서 얻게되는 장점은?
코드의 중복을 줄여 보다 편리하고 효과적으로 프로그래밍을 수행할 수 있다.

👻참조변수의 타입 변환
참조 변수도 타입변환이 가능하다.(멤버의 개수를 조절하는 것을 의미)

타입 변환을 위한 조건은?
1. 서로 상속관계에 있는 상위 클래스 - 하위 클래스 사이에만 타입 변환이 가능하다.
2. 하위 클래스 타입에서 상위 클래스 타입으로의 타입 변환(업캐스팅)은 형변환 연산자(괄호)를 생략할 수 있다.
3. 반대로 상위 클래스에서 하위 클래스 타입으로 변환(다운캐스팅)은 형변환 연산자(괄호)를 반드시 명시해야한다.

정리하면, 참조변수의 타입변환은 서로 상속 관계에 있는 관계에서는 양방향으로 자유롭게 수행될 수 있으나, 상위 클래스로의 타입 변환이냐(타입 변환 연산자 생략 가능) 아니면 하위 클래스로의 타입 변환이냐(타입 변환 연산자 생략 불가)에 따라서 약간의 차이가 있다.

👻instanceof 연산자
instanceof 키워드는 참조변수의 타입 변환, 즉 캐스팅이 가능한 지 여부를 boolean 타입으로 확인할 수 있는 자바의 문법요소이다.
캐스팅 가능 여부를 판단하기 위해서는 두 가지, 즉 ‘객체를 어떤 생성자로 만들었는가’와 ‘클래스 사이에 상속관계가 존재하는가’를 판단해야 한다.
만약 참조_변수 instanceof 타입을 입력했을 때 리턴 값이 true가 나오면 참조 변수가 검사한 타입으로 타입 변환이 가능하며, 반대로 false가 나오는 경우에는 타입 변환이 불가능하다.

👻추상화(Abstraction)
추상화는 기존 클래스들의 공통적인 요소들을 뽑아서 상위 클래스를 만들어 내는 것이라고 할 수 있다.
물론 공통적인 속성과 기능을 정의하고 하위 클래스들을 생성할 수도 있다.

👻abstract 제어자
abstract는 주로 클래스와 메서드를 형용하는 제어자인데, 메서드 앞에 붙은 경우를 ‘추상 메서드(abstract method)’, 클래스 앞에 붙은 경우를 ‘추상 클래스(abstract class)’라 각각 부른다.
어떤 클래스에 추상 메서드가 포함되어있는 경우 해당 클래스는 자동으로 추상 클래스가 된다.
ex)
abstract class AbstractExample { // 추상 메서드가 최소 하나 이상 포함돼있는 추상 클래스
   abstract void start(); // 메서드 바디가 없는 추상메서드
}
위와같이 추상 메서드 는 메서드의 시그니처만 있고 바디가 없는 메서드를 의미한다.
또한 추상 클래스는 미완성 설계도이기 때문에 메서드 바디가 완성이 되기 전까지 이를 기반으로 객체 생성이 불가하다.

👻추상 클래스
미완성 클래스를 만드는 이유는?
1. 추상 클래스는 상속 관계에 있어 새로운 클래스를 작성하는데 매우 유용하다.
메서드의 내용이 상속을 받는 클래스에 따라서 종종 달라지기 때문에 상위 클래스에서는 선언부만을 작성하고, 실제 구체적인 내용은 상속을 받는 하위 클래스에서 구현하도록 비워둔다면 설계하는 상황이 변하더라도 보다 유연하게 대응할 수 있다.
이 때 우리가 사용하게 되는 것이 ‘오버라이딩' 이다. 
즉, 추상 클래스를 사용하면 상속을 받는 하위 클래스에서 오버라이딩을 통해 각각 상황에 맞는 메서드 구현이 가능하다는 장점이 있다.
2. 추상 클래스는 추상화를 구현하는데 핵심적인 역할을 수행한다.
그렇기에 만약 여러 사람이 함께 개발하는 경우, 공통된 속성과 기능임에도 불구하고 각각 다른 변수와 메서드로 정의되는 경우 발생할 수 있는 오류를 미연에 방지할 수 있다.

결론적으로 상속계층도의 윗쪽에 위치할 수록 추상화의 정도가 높고 그 아래로 내려갈수록 구체화된다고 생각할 수 있다. 즉, 위에 있을수록 더 공통적인 속성과 기능들이 정의되어 있는 것이다.

👻final 키워드
‘최종의', ‘마지막의'라는 뜻을 가지고 있는 final 키워드는 필드, 지역 변수, 클래스 앞에 위치할 수 있으며 그 위치에 따라 그 의미가 조금씩 달라진다.
- 클래스 : 변경 또는 확장 불가능한 클래스, 상속 불가
- 메서드 : 오버라이딩 불가
- 변수 : 값 변경이 불가한 상수

👻인터페이스
인터페이스는 어떤 두 대상 간의 연결 내지 소통을 돕는 중간 가교 역할을 수행하는 것이다.
인터페이스도 추상 클래스와 같이 객체 지향의 추상화를 구현한다는 점에서 비슷한 역할을 수행하지만 인터페이스는 추상클래스보다 더 높은 추상성을 가지고 있다.
추상 클래스가 구현부가 미완성된 추상 메서드와 멤버 변수를 포함 할 수 있는 반면에 인터페이스는 오직 추상 메서드와 상수만을 멤버로 가질 수 있고 다른 어떤 요소 포함될 수 없다.
인터페이스를 작성하는 것은 기본적으로 클래스를 작성하는 것과 유사하지만, class 키워드 대신 interface 키워드를 사용한다는 점에서 차이가 있다.
또한 일반 클래스와 다르게, 내부의 모든 필드가 public static final로 정의되고, static과 default 메서드 이외의 모든 메서드가 public abstract로 정의된다는 차이가 있다.
다만 모든 인터페이스의 필드와 메서드에는 위의 요소가 내포되어있기 때문에 명시하지 않아도 생략 가능하다.

👻인터페이스의 구현
어떤 클래스가 어떤 인터페이스를 구현한다는 것은 그 인터페이스가 가진 모든 추상 메서드들을 해당 클래스 내에서 모두 오버라이딩해야 함을 의미한다.
클래스 간의 상속은 단 하나만 가능하다. 즉, 하위 클래스는 단 하나의 상위 클래스만 상속받을 수 있다.
그러나 인터페이스는 다중적 구현이 가능하다. 정리하자면, 하나의 클래스는 여러 개의 인터페이스를 구현할 수 있다.

왜 클래스는 다중 상속이 불가능한데, 왜 인터페이스는 여러 개를 구현해도 되는걸까?
클래스에서 다중 상속이 불가능했었던 이유는 만약 부모 클래스에 동일한 이름의 필드 또는 메서드가 존재하는 경우 충돌이 발생하기 때문인데, 인터페이스는 애초에 미완성된 멤버를 가지고 있기 때문에 충돌이 발생할 여지가 있을 수 없고 따라서 다중적 구현이 가능한 것이다.

오늘은 객체지향 중에서도 제일 중요하다고도 말해지는 다형성과 추상화에 대해 학습했다.
깊지 않은 기본 개념들만 학습한 기분이 들어 따로 추가적으로 공부를 했었는데, 부모 클래스와 자식 클래스가 복합적으로 되어있어 정말 어렵다 라고 느꼈고, 내가 과연 혼자서 이러한 코드들을 입력할 수 있을까?란 생각도 들었다. 물론 이론만 봐서는 알 수 없기에 추후에 페어 프로그래밍, 여러 프로젝트들을 통해 익숙해지는 것이 답이라고 생각한다. 그날까지 절대 멘탈 흔들리지 말고 힘내보자 나 자신아
오늘도 고생했어!

profile
개발 공부

0개의 댓글