기범_Alex
beom's 기술저장소
기범_Alex
전체 방문자
오늘
어제
  • 분류 전체보기 (13)
    • Computer-Science (4)
      • 네트워크 (3)
      • 자료구조 (1)
    • Programming (4)
      • Java (2)
      • Spring (1)
      • IDE (1)
    • Database (3)
      • InfluxDB (3)
    • ETC (1)
    • 단순 끄적임.. (1)

블로그 메뉴

  • 🏠 홈
  • 💻 Github
  • 🖋️ 방명록

인기 글

최근 글

hELLO · Designed By 정상우.
기범_Alex

beom's 기술저장소

객체 지향, 그 속으로
Programming/Java

객체 지향, 그 속으로

2022. 9. 6. 02:34
📢 백엔드 관련 자료는 Backend Wiki에서 PR을 통해 검증과 내용 보완을 거친 후 블로그로 이관되고 있습니다 :)

 

객체 지향 이론 기본 개념

  • 객체 지향 프로그래밍 = 실제 세계를 컴퓨터 속에 옮겨 놓기
    1. 실제 사물의 속성과 기능을 분석
    2. 데이터(변수)와 함수로 정의
    3. 필요한 사물끼리 연결
  • 실제 세계는 사물(객체)로 이루어져 있으며, 발생하는 모든 사건들은 사물 간의 상호작용입니다
  • OOP (캡슐화, 상속, 추상화, 다형성) 개념을 중심으로 점차 구체적으로 발전되었습니다

 

객체 지향 언어란?

  • 기존의 프로그래밍 언어(절차적 언어)에서 몇 가지 새로운 규칙을 추가한 언어입니다
  • 코드의 재사용성이 높고 유지보수가 용이하며, 중복 코드 제거할 수 있는 특징이 있습니다

 

객체 지향 언어 주요 특징

  1. 코드의 재사용성이 높습니다
    • 새로운 코드를 작성할 때 기존의 코드를 이용하여 쉽게 작성할 수 있습니다
  2. 코드의 관리가 용이합니다
    • 코드 간의 관계를 이용해서 적은 노력으로 쉽게 코드를 변경할 수 있습니다
  3. 신뢰성이 높은 프로그래밍을 가능하게 합니다
    • 제어자, 메서드를 이용하여 데이터를 보호하고 올바른 값을 유지하도록 합니다
    • 코드의 중복을 제거하여 코드의 불일치로 인한 오동작을 방지합니다

 

객체 지향 프로그래밍 특징 - OOP

객체 지향 프로그래밍의 4대 특징을 간단하게 알아보겠습니다

 

캡슐화 (Encapsulation)

  • 공통된 데이터와 데이터를 활용하는 함수끼리 캡슐(Class) 안에 두는 것
    • 즉 개념 혹은 논리적으로 연관된 데이터(변수)와 함수를 하나의 클래스에 캡슐화하는 것을 의미합니다
  • 클래스 안에서는 표시할 속성(public 변수)와 숨길 속성(private 변수)을 선택할 수 있습니다
특징 설명
데이터 캡슐화 필드와 메서드를 하나로 묶는 것
은닉화 외부에 드러나게 하지 않기를 원하는 데이터를 감추어(private) 외부에서 데이터를 직접 접근하는 것을 방지
class TV {
      int channel;
      // 가격은 getPrice()를 통해서만 가져갈 수 있다 -> 직접 접근 불가
      private int price;
      String color;

      void channelUp() {
          this.channel++;
      }

      public int getPrice() {
          return price;
      }

      public void setColor(String color) {
          this.color = color;
      }
}

 

상속 (Inheritance)

  • 부모 클래스의 특징과 기능을 자식 클래스에게 물려주는 것
  • 코드를 더 작은 단위로 Class를 쪼개면서 재사용을 할 수 있습니다
  • 공통적인 요소를 합쳐 중복 코드를 제거할 수 있습니다
  • 부모 클래스 수정 시 모든 자식 클래스도 일괄 수정되는 특징이 있습니다
class Entrepreneur {
    String firstName;
    String lastName;
    private int shares;
    private String company;
}

class Actor {
    String firstName;
    String lastName;
    private int oscars;
    private int age;
}

// firstName과 lastName이 공통적으로 사용되는 멤버이다 -> 상속
// ↓↓↓↓↓↓↓↓↓↓↓↓↓↓↓↓↓↓↓↓↓↓↓↓↓↓↓↓↓↓↓↓↓↓↓↓↓

class Person {
    String firstName;
    String lastName;
}

class Entrepreneur extends Person {
    private int shares;
    private String company;
}

class Actor extends Person {
    private int oscars;
    private int age;
}

 

추상화 (Abstraction)

  • 구현 세부 정보를 숨기고 일반 인터페이스를 지정하는 행위
  • 세부 사항(구현부)의 수정이 일어난다 하더라도 해당 메서드를 사용하는 다른 어느 곳에서도 수정을 할 필요가 없습니다
💡 예시를 들어보자

자동차에는 엑셀, 브레이크, 핸들, 버튼 등 다양한 인터페이스가 존재한다

우리는 아래와 같이 알 수 있다
엑셀: 차가 움직인다
브레이크: 차가 멈춘다
핸들: 차의 방향을 조절한다
버튼: 각각의 기능이 있다

하지만 구현 세부정보는 각 제조사마다 다르지만 우리는 몰라도 차를 운전하는데 전혀 지장이 없다.
따라서 인터페이스는 구현체 내부에서 어떻게 돌아가는지 몰라도 원하는 기능을 사용하는데 문제가 없다는 특징이 있다

 

다형성 (Polymorphism)

  • 여러 개의 형태를 갖고 있는 것
  • 즉 변수 혹은 메서드가 상황에 따라 다른 결과가 나옵니다
    • 오버로딩과 오버라이딩을 통해 해당 내용이 가능합니다
  • 메서드가 어떻게 작동해야 되는지에 대한 최소한의 규칙이 정해져 있습니다 (return 타입 등)
    • 메서드의 핵심은 보존하면서 구현 방식의 모양과 모습만 다르게 구현할 수 있는 방법입니다
class Person {
    public String sayHi() {
        return "ㅎㅇ";
    }

    public String sayBye() {
        return "ㅂㅂ";
    }
}

class 한국인 extends Person {
}

class Italian extends Person {
    @Override
    public String sayHi() { // 오버라이딩
        return "Hi!";
    }
}
public static void main(String[] args) {

    한국인 한국인1 = new 한국인();
    한국인1.sayHi(); // 출력값: ㅎㅇ
    
    Italian italian1 = new Italian();
    italian1.sayHi(); // 출력값: Hi!
}

이처럼 한국인 객체의 sayHi()와 Italian 객체의 sayHi()의 결과가 다른 것을 볼 수 있습니다

 

 

객체란?

  • 객체는 ‘실제로 존재하는 것’ 으로써 우리 주변에서 볼 수 있는 모든 사물들이 곧 객체라고 볼 수 있습니다
  • 개념이나 논리 같은 무형적인 것들도 포함됩니다
  • 프로그래밍 관점 → 클래스에 정의된 내용대로 메모리에 객체가 생성됨
  • 객체 = 속성(변수) + 기능(메서드)
객체 설명
객체의 정의 실제로 존재하는 것, 사물 또는 개념
객체의 용도 객체가 가지고 있는 기능과 속성에 따라 다름
유형의 객체 책상, 의자, 모니터 등과 같은 사물
무형의 객체 수학공식, 프로그램 에러와 같은 논리나 개념

 

클래스란?

  • 객체를 정의해놓은 것 → 객체의 설계도 또는 틀이라고 정의
객체 클래스
제품 제품 설계도
TV TV 설계도
붕어빵 붕어빵 기계
  • 클래스는 객체를 생성하는 데 사용됩니다
    • 자동차라는 객체가 필요하다고 가정해봅시다
    • 프로그래밍에서는 클래스를 먼저 작성한 후, 클래스로부터 객체를 생성하여 사용해야 합니다!

1. 자동차라는 클래스를 작성합니다 (설계도)

class Car {
     ....
}

2. 자동차라는 클래스를 통해 객체를 생성합니다 (인스턴스화)

Car car= new Car();
클래스는 서로 관련된 변수들을 정의하고 이들에 대한 작업을 수행하는 함수들을 함께 정의한 것입니다
클래스가 곧 사용자 정의 타입입니다 (기본 자료형 외) - (ex. VO, DTO)

 

객체와 인스턴스

  • 객체와 인스턴스는 같은 의미이다! -> 따라서 문맥에 따라 구별하여 사용하면 됩니다
💡 예시를 들어보자

차 인스턴스다 x -> 차 객체다 o
차는 차 클래스의 객체이다 x -> 차는 차 클래스의 인스턴스이다 O
  • 클래스 —— (인스턴스화) ——> 인스턴스(객체)
    • 클래스로부터 객체를 만드는 과정 → 클래스의 인스턴스화
    • A 클래스로부터 만들어진 객체 → A 클래스의 인스턴스
    // 클래스의 객체를 생성 -> 객체의 주소를 참조변수에 저장
    클래스명 변수명 = new 클래스명();
    
    Class Human { ... }
    
    // new를 통해 Human 인스턴스 생성 -> gibeom이라는 참조변수에 Human 인스턴스의 주소 저장
    Human gibeom = new Human();

 

참조 변수 vs 인스턴스

  • 인스턴스는 오직 참조 변수를 통해서만 다룰 수 있고, 참조 변수의 타입과 인스턴스의 타입은 당연히 일치해야 합니다
  • 하나의 인스턴스를 여러 개의 참조 변수가 가리키는 경우가 가능합니다
    • 아래 예시에서 gibeom2에 생성된 인스턴스는 gibeom1과 gibeom2이 동시에 가리키고 있습니다
Human gibeom1 = new Human();
Human gibeom2 = new Human();
gibeom1 = gibeom2   // 참조변수 gibeom1한테 gibeom2의 주소값을 부여

// gibeom1의 본래 주소값은 garbage collector에 의해 메모리 반환
  • 여러 인스턴스를 하나의 참조 변수가 가리키는 경우는 불가능합니다
    • 위 예시의 gibeom1처럼 덮어씌워집니다

 

객체의 구성 요소

  • 객체는 속성과 기능의 집합입니다
  • 객체가 가지고 있는 속성과 기능을 그 객체의 멤버(구성원, member)라고 합니다
구성 요소 명칭
속성 (property) 멤버 변수, 특성(attribute), 필드(field), 상태(state)
기능 (function) 메서드, 함수, 행위(behavior)

 

속성과 기능에 대한 예시 (TV)

속성 기능
크기, 길이, 높이, 무게, 색상, 볼륨, 채널 등 켜기, 끄기, 볼륨 높이기 낮추기, 채널 변경하기 등
채널 → int channel; 채널 변경하기 → channelUp() { … }
  • 같은 클래스 안의 멤버일지라도, 각 인스턴스의 속성(멤버변수)은 독립적으로 서로 다른 값을 유지합니다 → 서로 다른 객체 주소 값을 참조
  • 메서드의 행위는 모든 인스턴스에 대해 동일하게 동작합니다 (오버라이딩한 경우 제외)
Class Human {
	String gender;
	int age;

	void increaseAge()  { ++age; }
}

Class HumanTest {
	Human gibeom = new Human();
	Human beom = new Human();
	
	gibeom.increaseAge()

// 속성중에 하나인 멤버변수 age는 각 인스턴스마다 서로 다른 값을 유지
// 하지만 increaseAge 같은 메서드 동작 자체는 모든 인스턴스에서 동일하게 작동
	System.out.println(gibeom.age); // 1
	System.out.println(beom.age); // 0
}

 

 

객체 배열

  • 객체의 주소를 배열에 저장 → 즉 참조 변수들을 하나로 묵은 참조 변수의 배열
Human[] humanArr = {new Human(), new Human(), new Human()}

 


마무리

자바를 다시 공부하면서 객체, 클래스, 인스턴스, 참조 변수 등의 용어가 헷갈렸었던 것들이 재정비가 되는 느낌입니다

객체지향의 뿌리는 절차적 언어에서 시작됐다는 내용은 흥미로운 것 같네요

OOP의 캡!상추다 에 대해서도 다시 한번 상기시키며 개발을 할 때 참고해서 코드를 구성해야 될 것 같습니다

감사합니다 :)

 

 

 

📢 자료가 도움이 되셨다면 Backend Wiki로 놀러 오세요!

Reference

  • Java의 정석
  • 노마드 코더 - 객체지향 개념정리 10분컷
  • https://velog.io/@0sunset0/OOP의-네가지-특징추상화캡슐화상속다형성

 

💡 잘못된 내용이나, 보충할 내용이 있다면 언제든지 편하게 연락 주시면 감사하겠습니다 :)

🙋🏻‍♂️ Call me
Email : dev.gibeom@gmail.com
KakaoTalk : https://open.kakao.com/me/beomdrive

 

'Programming > Java' 카테고리의 다른 글

변수와 메서드, 그 속으로  (0) 2022.09.06
    'Programming/Java' 카테고리의 다른 글
    • 변수와 메서드, 그 속으로
    기범_Alex
    기범_Alex
    🌱 글을 통해 배운 것을 정리하고 지식을 공유합니다 🌱

    티스토리툴바