generated from muhandojeon/study-template
-
Notifications
You must be signed in to change notification settings - Fork 0
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
[박상범] 챕터 7: 자바스크립트 디자인 패턴 (1/3) #42
The head ref may contain hidden characters: "\uCC55\uD1307_1/\uBC15\uC0C1\uBC94"
+143
−0
Merged
Changes from all commits
Commits
File filter
Filter by extension
Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,143 @@ | ||
# 챕터7 자바스크립트 디자인 패턴 | ||
|
||
## 7.1 생성 패턴 | ||
- 생성자 패턴 | ||
- 모듈 패턴 | ||
- 노출 묘듈 패턴 | ||
- 싱글톤 패턴 | ||
- 프로토타입 패턴 | ||
- 팩토리 패턴 | ||
|
||
## 7.2 생성자 패턴 | ||
- es6 출시 이후로 생성자 가진 클래스 만들 수 있게 됨 | ||
- 클래스는 자바스크립트가 가진 프로토타입의 상속을 이용한 문법적 설탕임 | ||
- 새 객체를 초기화하는 constructor() 메서드를 갖고 있어야 됨. new 키워드는 생성자 호출하고 생성자 내부의 this는 새로 생성된 해당 객체 가리킴 | ||
|
||
```js | ||
class Car { | ||
constructor(...) { | ||
... | ||
} | ||
toString() { | ||
} | ||
} | ||
``` | ||
|
||
생성자 기본 예제인데 여기서 몇가지 문제 있음 | ||
- 상속 어려워짐 | ||
- 생성자로 인스턴스 생성하면 같은 함수 새로 정의하게 됨 | ||
|
||
```js | ||
class Car { | ||
constructor(...) { | ||
... | ||
} | ||
Car.prototype.toString = function() { | ||
} | ||
} | ||
``` | ||
|
||
이를 해결하기 위해 생성자의 프로토타입에 메서드 추가하면 됨. 그러면 공유함 | ||
|
||
## 7.3 모듈 패턴 | ||
객체 리터럴 => 우리가 흔히 작성하는 방식 | ||
|
||
es10 이전엔 접근 제한자(#)가 없었어서 변수 비공개 개념이 존재하지 않았음 | ||
=> 이걸 함수 스코프를 이용해 비공개 개념을 구현함. 선언된 모듈 내부에서만 변수, 메서드 사용 가능 | ||
=> 근데 반환되는 객체에 포함된 변수, 메서드는 공개되잖아? | ||
=> 반환된 객체에 포함된 변수를 비공개하려면 WeakMap() 사용하면 됨 | ||
|
||
> [예제 링크](https://developer.mozilla.org/ko/docs/Web/JavaScript/Reference/Global_Objects/WeakMap#%EB%B9%84%EA%B3%B5%EA%B0%9C_%EB%A9%A4%EB%B2%84_%ED%9D%89%EB%82%B4%EB%82%B4%EA%B8%B0) | ||
아래 처럼 모듈 내에서 변수를 내보내지 않고 비공개로 사용 가능 ㄷ ㄷ | ||
|
||
```js | ||
let _counter = new WeakMap(); | ||
|
||
class Module { | ||
constructor() { | ||
// 비공개 카운터 변수 | ||
_counter.set(this, 0); | ||
} | ||
incrementCounter() { | ||
let counter = _counter.get(this); | ||
counter++; | ||
_counter.set(this, counter); | ||
return _counter.get(this); | ||
} | ||
resetCounter() { | ||
console.log(`counter value prior to reset: ${_counter.get(this)}`); | ||
_counter.set(this, 0); | ||
} | ||
} | ||
|
||
const testModule = new Module(); | ||
``` | ||
|
||
믹스인 가져오기 변형, 내보내기 변형.. 시간이 지나면서 각자의 입맛에 맞는 모듈 패턴의 변형들이 등장하기 시작함 | ||
|
||
### 장점 | ||
- 초보 개발자들도 이해하기 쉬움 (중요!) | ||
- 사용하기 쉽고 모듈 사이의 의존성 관리하고 전역 요소를 원하는 만큼만 넘겨주어 유지보수 용이하게 됨 | ||
- 바깥으로 노출 안하면 모듈 내부에 비공개로 유지 | ||
|
||
### 단점 | ||
- 필요한 오류를 고칠 때 복잡도를 높일 수가 있다 | ||
|
||
## 7.4 노출 모듈 패턴 | ||
일만이 행님이 답답해서 만든 패턴 | ||
|
||
비공개 함수와 속성에 접근하는 공개 포인터를 만듦. | ||
이렇게 하면 모듈 가장 아래에 위치한 공개 객체를 더 알아보기 쉬워서 가독성 좋음 | ||
|
||
> 회사에서도 커스텀 훅은 다 노출 모듈 패턴으로 작성함 | ||
|
||
## 7.5 싱글톤 패턴 | ||
클래스의 인스턴스가 오직 하나만 존재하도록 제한하는 패턴 | ||
|
||
주의할 점은 실근톤이 '객체'나 '클래스'가 아닌 '구조'라는 점. 클로저 변수 변수 자체가 클로저가 아니라 클로저 제공하는 함수 스코프가 클로저를 뜻하는 거처럼.. | ||
|
||
```js | ||
constructor() { | ||
if (this._instance == null) { | ||
if ( isFoo() ) { | ||
this._instance = new FooSingleton(); | ||
} else { | ||
this._instance = new BasicSingleton(); | ||
} | ||
} | ||
return this._instance; | ||
}; | ||
``` | ||
|
||
싱글톤은 지연된 실행이 중요! | ||
|
||
싱글톤을 정적 인스턴스로 구현했다 하더라도, 필요할 때까지는 리소스나 메모리를 소모하지 않도록 지연 생성 될 수 있다고 함 | ||
|
||
리액트에선 싱글톤 대신 context API 나 리덕스 같은 전역 상태 관리 도구 이용하여 개발 함 | ||
|
||
## 7.6 프로토타입 패턴 | ||
이미 존재하는 객체를 복제해 만든 템플릿을 기반으로 새 객체를 생성하는 패턴 | ||
|
||
자바스크립트만이 가진 고유의 방식으로 작업 가능함 | ||
|
||
프로토타입 패턴은 상속 구현하는 쉬운 방법이면서 성능상 이점도 챙기기 가능 | ||
=> 객체 내에 함수를 정의할 때 복사본이 아니라 참조로 생성되어 모든 자식 객체가 동일한 함수 가리키게 할 수 있음 | ||
|
||
## 7.7 팩토리 패턴 | ||
|
||
### 사용하면 좋은 상황 | ||
- 객체나 컴포넌트 생성의 복잡성을 가질 때 | ||
- 다양한 객체를 생성해야 할 때 | ||
- 같은 속성을 공유하는 작은 객체를 다룰 때 | ||
- 덕타이핑 같은 api 규칙만 충족하면 되는 다른 객체 인스턴스와 객체를 구성할 때 | ||
|
||
### 사용하면 안되는 상황 | ||
- 객체 생성 과정이 인터페이스 뒤에 추상화하기 때문에 생성과정이 복잡할 경우 사용하지 마라 | ||
|
||
## 추상 팩토리 패턴 | ||
|
||
같은 목표를 가진 각각 팩토리를 하나의 그룹으로 캡슐화하는 패턴 | ||
|
||
추상 팩토리는 자동차나 트럭같은 차량 타입만 정의, 구체적 팩토리는 차량의 공통 기능을 충족하는 클래스만 구현 |
Oops, something went wrong.
Add this suggestion to a batch that can be applied as a single commit.
This suggestion is invalid because no changes were made to the code.
Suggestions cannot be applied while the pull request is closed.
Suggestions cannot be applied while viewing a subset of changes.
Only one suggestion per line can be applied in a batch.
Add this suggestion to a batch that can be applied as a single commit.
Applying suggestions on deleted lines is not supported.
You must change the existing code in this line in order to create a valid suggestion.
Outdated suggestions cannot be applied.
This suggestion has been applied or marked resolved.
Suggestions cannot be applied from pending reviews.
Suggestions cannot be applied on multi-line comments.
Suggestions cannot be applied while the pull request is queued to merge.
Suggestion cannot be applied right now. Please check back later.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
대략 이런 모습으로 이해하면 될까요??
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
맞아요 전 아래와 같이 좀 더 일반적인 커스텀 훅 형태를 생각했어요!
노출 모듈 패턴이 실제로 커스텀 훅과 완전 일치하지 않을 수 있지만! 노출 모듈 패턴의 개념적 특성을 일부 따르고 있다고 봤어요
특히 내부 상태를 캡슐화하고 외부에는 필요한 값만 노출한다는 점에서 유사하다고 생각했슴다
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
아아 말씀하신대로 이렇게도 적용 예로 볼 수 있겠군요 ?!? 👍 👍