본문 바로가기
Research/Computer Science

OOP(Object-Oriented Programming)

by RIEM 2023. 3. 27.

OOP란 무엇이고, 다른 프로그래밍 패러다임과 어떤 차이가 있나?

OOP는 프로그램 패러다임 중 하나이다. 프로그래밍 패러다임의 유형을 예로 들라 하면 Procedule, Functional, OOP 이 3개가 대표적으로 거론됩니다.

프로그래밍 패러다임을 구분하면 이렇습니다.

  • 명령형(How)
    • 절차지향 : 순차적인 처리 과정에 집중. C, C++
    • 객체지향 : 객체들의 집합으로 상호작용에 집중. C++, Java, C#, Python, Swift, Ruby, Perl, ...
  • 선언형(What)
    • 순수 함수를 조합하는데 집중. Closure, Haskel, Lisp, ...

명령형에서 절차 지향이 컴퓨터 친화적이면 객체지향은 개발자 친화적인 패러다임이라고 보면 됩니다.

Procedule(절차형) 프로그래밍

프로그램 역사의 초기에 주로 사용되던 패러다임이다. 컴퓨터의 처리 흐름과 코드의 흐름이 유사해서 실행속도가 빠르고 디버깅도 쉽다는 장점이 있다. 하지만 컴퓨터 성능이 증가하고 유지보수 및 개발 편의성에 대한 니즈가 증가하면서 OOP 패러다임이 각광받기 시작한다.

Functional(함수형) 프로그래밍

기본 명령형 프로그래밍 방식에서 발생하는 스파게티 코드 문제를 개선하기위해 개발자들이 열심히 고민한 결과 함수형 프로그래밍이라는 대안이 나타났다. 문제를 해결하기 위한 도구로 '함수'를 사용하여 가독성을 높이고 유지보수를 쉽게 만든다. assignment statement가 없는 프로그래밍 방법론이라고 클린코드의 저자 Rober C.Martin는 언급했다.

OOP(객체지향) 프로그래밍

OOP(Object-Oriented Programing)은 클래스나 객체를 활용하여 소프트웨어를 작은 부품(Componenets) 단위로 쪼개는 개발 패러다임을 의미합니다. 최근 가장 많이 쓰이는 방법론입니다.

OOP 언어에서 객체는 클래스의 인스턴스를 지칭합니다. 클래스에 값과 메소드를 캡슐화하고, 인스턴스는 이를 사용합니다. OOP의 구성 요소는 class, attribute, method 등이 있는데요, 이를 예로 들어보겠습니다.

class : Car
attribute : name, company, model, type, ...
method : drive, park, ...

자동차는 너무 식상하니 우리 패션 브랜드를 예시로 클래스를 만들어보겠습니다.

class Brand {
  constructor(brandName, launchYear) {
    this.brandName = brandName;
    this.launchYear = launchYear;
  }

  _members = 0;

  addMember() {
    this._members++;
    return this._members;
  }

  countMember() {
    console.log(`We have ${this.addMember()} people in our team.`)
  }

  introduce() {
    return console.log(`Welcome to ${this.brandName}. Our brand is founded in ${this.launchYear}. Please feel free to walk around.`)
  }
}

const hermes = new Brand('Hermes', 1837);

hermes.addMember();
hermes.addMember();
hermes.addMember();
hermes.countMember(); // We have 4 people in our team.
hermes.introduce(); // Welcome to Hermes. Our brand is founded in 1837. Please feel free to walk around.

OOP의 특징

OOP의 특징 4가지는 encapsulation, inheritance, polymorphism, abstraction이 있다.

Encapsulation(캡슐화)

어트리뷰트들이나 메소드들을 하나의 유닛으로 감싸는 것을 의미한다. 메소드나 어트리뷰트들은 private 또는 public 상태로 지정할 수 있는데, 캡슐화를 하면 private한 상태를 적용하여 외부에서 접근을 할 수 없게 만들 수 있다.

Abstraction(추상성)

외부에서 클래스의 기능은 사용할 수 있지만 그 외 나머지 세부 내용은 가려서 추상화하는 것을 말한다.

Inheritance(상속)

클래스로부터 어트리뷰트나 메소드들을 상속 받을 수 있다는 것은 재사용을 통해 반복을 줄일 수 있음을 의미한다. 공통적으로 쓰이는 로직, 구조 등은 수직 구조로 물려줄 수 있다. 생물의 DNA를 물려받는 것과 비슷하다.

Polymorphism(다형성)

같은 이름을 객체들이 각기 다른 기능이나 구조를 가질 수 있음을 의미한다. function 오버로딩 또는 오버라이딩 등에 주로 쓰인다.

OOP 설계 5원칙 SOLID

SOLID는 객체지향 설계에서 지켜야할 원칙 5개를 의미한다. 객체를 잘 사용하는 가이드라인으로 보면 되겠다.

SRP(Single Responsibility Principle) : 단일 책임 원칙
OCP(Open Closed Principle) : 개방 폐쇄 원칙
LSP(Listove Subsittution Principle) : 리스코프 치환 원칙
ISP(Interface Segregation Principle) : 인터페이스 분리 원칙
DIP(Dependency Inversion Principle) : 의존 역전 원칙

SOLID 원칙은 디자인 패턴, 아키텍처 설계 등에 근간이 되는 개념이여서 꼭 알아두어야 한다.

좋은 설계는 급박한 요구사항에 유연하게 대처하고, 확장성이 있는 시스템 구조를 만들 수 있게 해준다. SOLID 객체 지향 원칙을 적용하면 좋은 설계가 가능해진다. SOLID는 코드 확장, 유지보수 관리의 편의성, 불필요한 복잡도 감소하여 개발 생산성도 높아진다.

단일책임원칙, SRP(Single Responsibility Principle)

클래스는 하나의 기능만 담당하여, 하나의 책임만 지도록 설계한다. 책임 변경 시 다른 책임들을 수정해야 할 필요가 없어지기 때문에 유지보수가 편해진다.

개방 폐쇄 원칙, OCP(Open Closed Principle)

확장은 열려있으나, 수정에는 닫혀있어야 한다. 새로운 기능을 추가해야 할 때 클래스를 확장하여 기능을 추가할 수 있다. 하지만 확장에 따른 클래스 수정은 최소화해야 한다. OOP의 특징인 다형성과 확장성을 살리는 설계 원칙이다.

리스코프 치환 원칙, LSP(Liskov Substitution Principle)

다형성의 원리를 이용하는 원칙으로 자식 타입은 부모 타입으로 교체해도 의도대로 실행되어야 한다.

인터페이스 분리 원칙, ISP(Interface Segregation Principle)

Interface는 클라이언트의 목적과 용도에 따라 나눠야 한다. SRP이 클래스의 단일 책임에 집중하는 원칙이라면, ISP는 인터페이스의 단일 책임에 집중하는 원칙이다.

의존 역전 원칙, DIP(Dependency Inversion Principle)

DIP 원칙은 어떤 Class 참조해야 할 시 대상의 상위 요소(추상 클래스나 인터페이스)를 참조해야 하는 원칙을 말한다.자주 바뀌는 하위 모듈보다 아닌 잘 안바뀌는 상위 인터페이스에 의존을 해야한다.

OOP의 장단점

장점

  • 코드의 재사용성이 좋다. 객체를 모듈처럼 쓰기 때문에 다른 로직에서 이리저리 써먹기 좋다.
  • 유지보수가 간편하다. 객체 하나만 수정하면 이를 상속받은 인스턴스도 모두 수정할 수 있기 때문이다. 즉, 원본만 수정하는 간편한 방식이다.
  • 큰 프로젝트에 유용하다. 모듈 단위로 관리하기 때문에 개발자 간 작업을 나누기가 쉽고 도식도 편하다.

단점

  • 속도가 느리다. 절차 지향과 달리 서로 의존하는 객체 지향 프로그래밍은 상대적으로 느리다
  • 개발 역량이 필요하다. 모듈의 연관성을 잘 고려하지 않으면 오히려 복잡도가 증가할 수도 있다.
  • 복잡도. 객체, 상속, 인터페이스 등으로 의존 관계가 복잡하게 얽히면 코드 파악이 어려워진다

Reference

'Research > Computer Science' 카테고리의 다른 글

Parameter와 Argument의 차이  (0) 2023.03.30
MSA(MicroService Architecture)  (0) 2023.03.29
DB 인덱스  (0) 2023.03.28
Dependency Injection  (0) 2023.03.28
REST API  (0) 2023.03.27

댓글