해당 게시글은 맨 밑의 참고자료 링크를 기반으로 재구성한 것입니다.
0. 객체지향 프로그래밍
객체지향 프로그래밍은 프로그램을 명령어 또는 함수의 목록으로 보는 전통적인 명령형 프로그래밍의 절차지향적 관점에서 벗어나 여러 개의 독립적 단위, 즉 객체의 집합으로 프로그램을 표현하려는 프로그래밍 패러다임을 말한다. (모든 것이 객체로 그룹화된다)
사람이 세계를 보고 이해하는 방법과 흡사하다. 현대의 프로그래밍 언어 대부분이 해당한다(Java,C++,C# 등)
(프로그래밍에서 필요한 데이터를 추상화 시켜 상태와 행위를 가진 객체로 만들고, 객체들간의 상호작용을 통해 로직을 구성하는 프로그래밍)
이미지 출처 : https://www.reddit.com/r/ProgrammerHumor/comments/418x95/theory_vs_reality/
🔸객체지향의 특징
1) 추상화 (Abstraciton)
- 객체에서 공통된 속성과 행위를 추출 하는 것
- 추상화는 불필요한 정보는 숨기고 중요한 정보만을 표현함으로써 프로그램을 간단하게 만드는 것
- class를 설계하는 것도 추상화에 해당한다.
추상화가 왜 필요할까?
'현대'와 같은 다른 자동차 브랜드가 추가될 수도 있다. 이때 추상화로 '자동차'를 구현 해놓으면 다른 곳의 코드를 수정할 필요 없이 추가로 만들 부분만 새로 생성해주면 된다.
2) 캡슐화 (Encapsulation)
- 데이터(속성)과 기능(메서드)을 따로 정의하는 것이 아닌 하나의 객체 안에 넣어서 묶고, 외부에서 직접적으로 접근하지 못하도록 은닉하는 개념을 말한다.
- 이를 통해 프로그래밍의 안전성을 높일 수 있다. 특정 프로퍼티에 대한 접근을 미리 정해진 메소드들을 통해서만 가능하게 하는 것. 캡슐화는 객체 외부에서 함부로 접근하면 안되는 프로퍼티나 메소드에 직접 접근할 수 없도록한다.
기본적으로 JavaScript 클래스에서 정의된 필드와 메서드는 public입니다. 즉, 클래스의 인스턴스를 통해 접근하고 수정할 수 있다. 그러나 때때로 특정 필드 또는 메서드를 클래스 외부에서 접근하지 못하게 만들어야 하는 경우가 있다. 이런 경우를 위해 # 기호를 사용하여 private 필드를 선언할 수 있습니다.
private 필드는 클래스 내부에서만 접근 가능하므로 캡슐화를 가능하게 한다. 이는 객체의 내부 상태를 외부에서 직접 수정하지 못하게 하여 객체의 무결성을 유지하는데 중요한 역할을 한다.
class Example {
#privateField;
constructor() {
this.#privateField = "I'm private!";
}
printPrivateField() {
console.log(this.#privateField);
}
}
const example = new Example();
example.printPrivateField(); // "I'm private!" 출력
console.log(example.#privateField); // 오류 발생: Uncaught SyntaxError: Private field '#privateField' must be declared in an enclosing class
위 예에서 #privateField는 Example 클래스 내부에서만 접근할 수 있습니다. 이 필드에 직접 접근하려고 하면 오류가 발생합니다. 그러나 클래스 내부에서 정의된 printPrivateField 메서드를 통해 간접적으로 접근할 수 있습니다. 이러한 방식을 통해 클래스의 내부 상태를 보호하고 제어할 수 있습니다.
3) 상속 (Inheritance)
- 부모 클래스의 프로퍼티와 메소드를 자식 클래스가 그대로 물려받는 것
4) 다형성 (Polymorphism)
- 하나의 부모 클래스를 상속받은 자식 클래스들이 "다양한 형태"를 가질 수 있다는 뜻
- 부모 클래스로 부터 상속받지만, 다형성을 통해서 각자의 방식대로 동작할 수 있다.
- 상속과 연관이 깊은 개념으로, 상속을 통해 부모 클래스의 메서드를 자식 클래스에서 재정의(오버라이딩)하거나, 인터페이스를 구현하는 여러 클래스가 각자의 방식으로 메서드를 구현하는 등의 다양한 형태를 가질 수 있다.
오버라이딩 : 상위 클래스가 가지고 있는 메소드를 하위 클래스가 재정의해서 사용하는 것
1. 프로토타입 기반 객체지향 프로그래밍
- 자바스크립트는 객체지향/명령형/함수형 프로그래밍을 지원하는 멀티 패러다임 프로그래밍 언어이다.
- 클래스 기반 객체지향 프로그래밍 언어와 달리 프로토타입 기반의 객체지향 프로그래밍이다.
🔸프로토타입 기반 언어
- 클래스 기반 언어에서 상속을 사용하는 것과 다르게, 객체를 원형(프로토타입)으로 하는 복제 과정을 통해 객체의 동작 방식을 재사용 할 수 있게한다.
(자바스크립트에서도 ES6 에서 'class' 키워드가 도입되었다. 하지만, 이는 클래스 기반언어와 같은 전통적인 클래스 기반 상속을 구현한것이 아니라, 프로토타입 기반 상속을 더 쉽게 구현하기 위한 문법적 설탕(syntatic sugar) 이다. 자바스크립트의 'class' 는 여전히 내부적으로는 프로토타입을 이용한다)
즉, 원본 객체가 존재하고 그 객체를 복제해서 새로운 객체를 생성하는 방법이다.
원본 객체를 복제해서 새로운 객체 생성하는거라는데...
🔸객체에 대해 더 자세히 알아보자
1️⃣아래처럼 리터럴로 객체를 선언하는 방법이 대부분일 것이다.
const eunhye = {
name: 'eunhye',
age: 29,
say: function () {
console.log(`Hi, I am ${this.name}!`);
}
};
2️⃣ 생성자함수로 객체를 생성하는 방법도 있다.
- Object 기본 내장 생성자함수로 객체 생성
(모든 객체의 프로토타입 최상위에 위치, 모든 객체는 'Object'의 프로토타입을 상속받는다)
const eunhye = new Object({name:'eunhye',age:29})
- 사용자 정의 생성자 함수
function Person(name, age) {
this.name = name;
this.age = age;
this.sayHi = function() {
console.log('안녕하세요, ' + this.name + '입니다.');
};
}
var person1 = new Person('John', 25);
person1은 Person 이라는 함수로 생성된 객체이다.
한줄평 : 객체는 함수로 만들어진다.
🔸그렇다면 원본 객체의 뭘 복제 하는것인가?
function User () {}
const eunhye = new User();
console.log(eunhye); //User {}
console.log(typeof eunhye); //object
위 코드를 보자.
eunhye 객체는 User 함수를 복제한 것이 아니라, User함수의 프로토타입 객체를 복사한 것이다.
함수를 통해 객체를 생성한다면서, 그러면 함수를 복제하는게 아닌가 하고 생각들겠지만 function 타입이 아닌 Object가 나온것을 봐선 Object타입을 복사했다는 것이다.
🔸함수가 생성될때는 해당 함수에 Constructor(생성자) 자격을 부여하고, 해당 함수의 Prototype Object를 생성하고 연결한다.
- 아래와 같이 User 라는 함수만 선언했는데, User.prototype 프로퍼티에 constructor 자격이 부여되고, Prototype 객체가 함께 생성 되는것을 볼 수 있다.
그리고 이 프로토타입 객체는 함수를 사용해서 새로운 객체를 생성할 때 원본 객체 역할을 해줄 객체를 의미한다.
즉, new User()라는 문법을 사용하여 새로운 객체를 만들게 되면 User 함수 자체가 아니라 User 함수가 생성될 때 함께 생성된 User 함수의 프로토타입 객체를 복제해서 새로운 객체를 만든다는 것이다.
참고자료
https://medium.com/@bluesh55/javascript-prototype-%EC%9D%B4%ED%95%B4%ED%95%98%EA%B8%B0-f8e67c286b67
https://ui.toast.com/weekly-pick/ko_20160603
https://evan-moon.github.io/2019/10/23/js-prototype/
'프론트엔드 개발 > JavaScript' 카테고리의 다른 글
자바스크립트) class 끝장 정리 (0) | 2023.06.21 |
---|---|
자바스크립트) strict 모드 (0) | 2023.06.20 |
자바스크립트) 프로토타입 (0) | 2023.06.19 |
자바스크립트) 함수형 프로그래밍 (0) | 2023.06.12 |
자바스크립트) 일급객체 (0) | 2023.06.12 |