디자인 패턴은 3가지 패턴으로 분류된다.
- 생성 패턴
- 객체 인스턴스를 생성하는 패턴, 즉 클라이언트와 그 클라이언트가 생성해야 하는 객체 인스턴스 사이의 연결을 끊어주는 패턴.
- 구조 패턴
- 클래스와 객체를 더 큰 구조로 만들 수 있게 구성을 사용하는 패턴.
- 행위 패턴
- 클래스와 객체들이 상호작용하는 방법과 역할을 분담하는 방법을 다르는 패턴.
자바스크립트 디자인 패턴 (링크)
constructor / builder pattern (생성자 / 빌더 패턴)
모든 언어에서의 Class 의 기능인 constructor(생성자) 의 기능이 디자인 패턴에 해당되는지 몰랐다.
class Example {
constructor(name, age, key) {
this.name = name;
this.age = age;
this.key = key;
}
}
const example1 = new Example("tony", 15, null);
const example2 = new Example("xrp", 20, null);
example1.key = example2;
console.log(example1); // 핵심
const example3 = new Example("ripple", 53, null);
example2.key= example3
console.log(example2)
실행결과->
Factory Pattern (팩토리 패턴)
- 단일 오브젝트를 만들기 위한 인터페이스를 정의하지만 서브 클래스가 인스턴스화할 클래스를 결정하도록 한다. 팩토리 메서드를 사용하면 클래스가 서브 클래스에 대한 인스턴스화를 연기할 수 있다.
의류 공장에서 셔츠를 달라고 하면 셔츠를 주는것과 같다.
신발을 달라고 하면 신발을 준다.
각각의 오브젝트들은 고유의 기능을 가지고 있다.
function AnimalFactory() {
this.createAnimal = function(animalType) {
let animal;
switch(animalType) {
case 'dog':
animal = new Dog();
break;
case 'cat':
animal = new Cat();
break;
case 'horse':
animal = new Horse();
break;
default:
animal = new Monkey();
break;
}
return animal;
}
}
const Dog = function() {
this.makeSound = () => {
console.log('woof woof!');
}
}
const Cat = function() {
this.makeSound = () => {
console.log('prrr prrr meow!');
}
}
const Horse = function() {
this.makeSound = () => {
console.log('neeeighhh!')
}
}
const Monkey = function() {
this.makeSound = () => {
console.log('ooooh ahh oooh oooh!');
}
}
const factory = new AnimalFactory();
const jojo = factory.createAnimal('dog');
jojo.makesound();
const tony = factory.craeteAnimal('cat');
tony.makesound();
const princess = factory.createAnimal('horse');
princess.makesound();
const kong = factory.createAnimal();
kong.makesound();
→ switch 문은 뭔가 구식의 문법이라고 여겼는데 그런 편견은 코딩할 때 불필요한 것 같다. 효율성을 우선시 하자!!
또한 위와 같이 하면 서브 클래스에서 인스턴스화를 할 수 있기에 편리한 것 같다.
Prototype Pattern ( 프로토타입 패턴)
- 프로토타입 인스턴스를 사용하여 생생할 오브젝트의 종류를 지정하고 기존 오브젝트의 ‘뼈대(skeleton)’에서 새 오브젝트를 생성하여 성능을 높이고 메모리 공간(footprints)을 최소화한다.
Javascript 의 멋진 기능이지만 프로토타입은 복잡하기에 아직까지 딥하게 하지는 않았다.
const macBook = {
color: 'silver',
turnOn() {
console.log('turning on...');
},
turnOff() {
console.log('turning off...');
}
}
// prototype 복제
const myComputer = Object.create(macBook, { owner: { value: 'Tim'} });
console.log(myComputer.__proto__ === macBook);
// 프로토타입 기반 복사X (객체의 프로퍼티에 값 주입)
const newComputer = {...macBook, owner: 'John'};
console.log(newComputer.__proto__ === macBook);
macBook.power = 'USB-C';
// 프로토타입에 새로운 값 'power' 을 넣었다.
console.log(myComputer.power);
// 하지만 non-prototype 이기에 안된다.
console.log(newComputer.power);
→ 자바스크립트의 프로토타입에 구조, 동작방식 을 이해해야 할 것 같다. JavaScript 가 굉장히 자유로운 언어라는 것을 실감한다.
Singleton Pattern (싱글톤 패턴)
- 클래스에 인스턴스가 하나만 있는지 확인하고 이에 대한 전역 액세스 포인트를 제공한다.
하나의 인스턴스만 있는지 확인하고 다른 인스턴스를 만드려고 시도하면 기존의 인스턴스를 참조(reference)를 반환한다.
const Database = (function () {
let instance;
function createDatabaseInstance() {
return new Object('Database Instance');
}
function getDatabaseInstance() {
if(!instance){
instance = createDatabaseInstance();
}
return instance;
}
return { getDatabaseInstance }
})();
const databaseInstance1 = Database.getDatabaseInstance();
const databaseInstance2 = Database.getDatabaseInstance();
console.log(databaseInstance1 === databaseInstance2)
행위 패턴
Command Pattern
요청을 오브젝트로 캡슐화하여 다른 요청이 있는 클라이언트의 매개 변수화와 요청 대기열 또는 로깅을 허용한다. 또한 실행 취소 할 수 있는 지원을 허용한다.
글쓴이 : 꽤 쉬워 보입니다. 그리고 저는 커맨드 오브젝트와 리시버(receiver)를 분리하는 것이 정말 좋습니다.
클린 코드를 만듭니다.
const calculatorMethods = {
add : function(n1,n2) {
return n1+n2;
},
sub: function(n1,n2) {
return n1-n2;
},
mul: function(n1,n2) {
return n1*n2;
},
div: function(n1,n2) {
return n1/n2;
}
}
const calculator = {
execute: function(method, num1, num2) {
if(!(method in calculatorMethods)) return null;
return calculatorMethods[method](num1,num2)
}
}
console.log(calculator('add',1,2));
console.log(calculator('sub',100,28));
console.log(calculator('mul',100,28));
console.log(calculator('div',100,28));
console.log(calculator('root',100,28));
Observer(Pub/Sub) Pattern
한 오브젝트의 상태가 변경되면 모든 종속 항목이 자동으로 알림을 받고 업데이트 되는 오브젝트 간의 일대다(one-to-many) 종속성을 정의합니다.
글쓴이 : 제 직감적인 생각은 이것이 제가 많이 가지고 놀지 않았던(적어도 잠시 동안) 자바스크립트의 “관찰 가능(observables)”을 생각하게 만든다는 것입니다. 이 패턴의 pub/sub 아이디어는 웹 소켓과 Redux도 생각하게 합니다.
class observer{
update(self){
pass
}
}
class Dog {
update(self){
console.log('dogdogdog')
}
}
class Cat {
update(self){
console.log('catcatcat');
}
}
class Owner{
constructor(){
self.animals = []
}
register(animal){
self.animals.push(animal)
}
notify(){
self.animals.forEach(animal => {
animal.update()
})
}
}
const owner = new Owner()
const cat = new Cat()
const dog = new Dog()
// owner 에서 observer(cat,dog) 등록
owner.register(cat);
owner.register(dog);
// owner 에서 notify를 통한 함수 호출을 알고 있자!!
owner.notift();
// 실전예제에서는 observer 들이 observer들을 가르키고 있는 경우도 있다.
// update 함수도 매우 많다.
템플릿 메소드 패턴
일부 단계를 서브 클래스로 지연하여 연산에서 알고리즘의 뼈대(skeleton)을 정의합니다.
템플릿 메서드를 사용하면 서브 클래스가 알고리즘의 구조를 변경하지 않고도 알고리즘의 특정 단계를 재정의할 수 있습니다.
내가 알고 있기론 상속을 통한 메소드 오버라이드를 한것 같은데 애매하다.
'프로그래멍 언어 > JavaScript' 카테고리의 다른 글
[프로젝트] 바닐라 JS 프로젝트 준비 (0) | 2024.02.18 |
---|---|
[Javascript] JS 이해하기 (0) | 2024.01.17 |