디자인 패턴

커맨드 패턴(Command Pattern)

JSKoder 2023. 3. 7. 22:31

Command 패턴은 메서드 호출, 요청 또는 작업을 단일 객체로 캡슐화할 수 있는 동작 디자인 패턴입니다.

명령이라고 하는 이 객체는 다른 메서드나 객체에 매개변수로 전달되어 저장되고 나중에 실행될 수 있습니다.

Command 패턴은 네 가지 주요 구성 요소로 이루어져 있습니다:

커맨드 패턴 용어

Receiver

  • 명령이 요청하는 작업을 실제로 수행하는 객체입니다.
  • Receiver는 초기화 중에 ConcreteCommand에 전달되며 멤버 변수로 저장됩니다.

Command

  • execute 메서드를 정의하는 인터페이스 또는 추상 클래스입니다.
  • execute 메서드는 명령이 실행될 때 수행할 작업을 지정합니다.
  • Command에는 실제 작업을 수행할 수신자 객체에 대한 참조도 포함됩니다.

Concrate Command

  • Command 인터페이스/추상 클래스를 구현하고 수신자 객체에 대한 참조를 포함하는 클래스입니다.
  • 이 클래스는 명령을 수행하기 위해 수신자 객체에서 적절한 메서드를 호출하여 execute 메서드를 구현합니다.

Invoker

  • 명령 객체 모음을 보관하고 실행 시기를 결정하는 객체입니다.
  • 인보커는 적절한 경우 Command 객체에서 execute 메서드를 호출할 책임이 있습니다.
import Foundation

//MARK: 모든 작업을 총괄하는 인터페이스
protocol Command {
    func execute()
}

//MARK: Concrete Command
struct LightOn: Command {
    private var receiver: Receiver
    
    init(receiver: Receiver) {
        self.receiver = receiver
    }
    
    func execute() {
        receiver.turnOn()
    }
}

//MARK: Concrete Command
struct LightOff: Command {
    private var receiver: Receiver
    
    init(receiver: Receiver) {
        self.receiver = receiver
    }
    
    func execute() {
        receiver.turnOff()
    }
}

struct Receiver {
    func turnOn() {
        print("불 켜기")
    }
    
    func turnOff() {
        print("불 끄기")
    }
}

struct Invoker {
    private var light: Command?
    
    mutating func setLightStatus(_ command: Command) {
        light = command
    }
    
    func requestWorking() {
        light?.execute()
    }
}

//MARK: Client
var invoker = Invoker()
let receiver = Receiver()
invoker.setLightStatus(LightOn(receiver: receiver))
invoker.requestWorking()
invoker.setLightStatus(LightOff(receiver: receiver))
invoker.requestWorking()

장점

  • 발신자와 수신자를 분리: 시스템의 다른 부분에 영향을 주지 않고 명령을 추가하거나 수정할 수 있습니다.
  • 그로인한 유연성이 높은 코드를 구현할 수 있습니다.
  • 새로운 명령을 쉽게 추가: 각 명령을 별도의 객체로 캡슐화하기 때문에 기존 코드를 수정하지 않고도 시스템에 새 명령을 추가할 수 있습니다.
  • 복잡한 시스템을 단순화: 복잡한 시스템을 더 작고 쉽게 관리할 수 있는 조각으로 분해하여 유지 보수 및 수정을 더 쉽게 할 수 있습니다.
  • 느슨한 결합을 촉진: 시스템의 전반적인 복잡성을 줄이고 테스트하기 쉽게 만듭니다.

단점

  • 복잡성 증가: 명령 패턴을 구현하면 명령의 수가 많거나 명령 자체가 복잡한 경우 시스템에 약간의 복잡성이 추가될 수 있습니다.
  • 메모리 사용량 증가: 명령 패턴은 많은 명령 객체가 생성되는 경우 메모리 사용량을 증가시켜 시스템 성능에 영향을 줄 수 있습니다.
  • 개발 시간 증가: 시스템이 이미 복잡하고 패턴을 구현하기 위해 리팩터링이 필요한 경우 Command 패턴을 구현하면 개발 시간이 늘어날 수 있습니다.