Menu
Coddy logo textTech

커맨드 패턴

Coddy PHP 여정의 객체 지향 프로그래밍 섹션에 포함된 레슨. 91개 중 75번째.

Command 패턴은 요청을 요청에 관한 모든 정보를 포함하는 독립 실행형 객체로 변환하는 행동 디자인 패턴입니다. 이러한 변환을 통해 요청을 메서드 인수로 전달하고, 요청 실행을 지연하거나 대기열에 추가하며, 실행 취소가 가능한 작업을 지원할 수 있습니다.

레스토랑을 생각해 보세요.

음식을 주문하면, 웨이터는 주문 내용을 전표(the command)에 적고, 그것을 주방으로 가져가며, 요리사는 이를 실행합니다. 웨이터는 요리하는 방법을 알 필요가 없으며, 그들은 just command를 전달할 뿐입니다.

이렇게 하면 요청자가 실행자와 분리됩니다.

기본적인 구현은 다음과 같습니다:

<?php
interface Command {
    public function execute(): string;
}
class Light {
    public function on(): string { return "Light is ON"; }
    public function off(): string { return "Light is OFF"; }
}
class LightOnCommand implements Command {
    public function __construct(private Light $light) {}
    
    public function execute(): string {
        return $this->light->on();
    }
}
class LightOffCommand implements Command {
    public function __construct(private Light $light) {}
    
    public function execute(): string {
        return $this->light->off();
    }
}

invoker는 명령이 무엇을 하는지 알지 못한 채 명령을 트리거합니다:

<?php
class RemoteControl {
    public function press(Command $command): string {
        return $command->execute();
    }
}
$light = new Light();
$remote = new RemoteControl();

echo $remote->press(new LightOnCommand($light)) . "\n";
echo $remote->press(new LightOffCommand($light));

출력:

Light is ON
Light is OFF

Command 패턴은 작업을 대기열에 추가하거나, 실행 취소 기능을 Implement하거나, 작업을 기록해야 할 때 뛰어난 효과를 발휘합니다. 각 command는 독립적으로 구성되어 있으므로 기존 코드를 수정하지 않고도 새로운 commands를 쉽게 추가할 수 있습니다.

challenge icon

챌린지

쉬움

Command Pattern을 사용하여 텍스트 편집기 command 시스템을 만들어 봅시다. 텍스트 편집기는 텍스트 작성, 텍스트 삭제, 작업 실행 취소와 같은 작업을 지원해야 하는 경우가 많습니다. 각 작업은 통합된 interface를 통해 execute할 수 있는 독립적인 command 객체가 됩니다.

코드를 네 개의 파일로 구성합니다.

  • Command.php: 단일 메서드 execute(): string를 포함하는 Command interface를 Define합니다. 이를 통해 모든 편집기 commands가 따라야 하는 contract가 establish됩니다.
  • TextEditor.php, receiver, 즉 실제로 작업을 수행하는 객체를 나타내는 TextEditor class를 Create합니다. 편집기는 다음을 수행해야 합니다.
    • current 텍스트 content를 저장합니다(처음에는 empty string으로 시작).
    • 텍스트를 content에 추가하고 "Written: [text]"를 반환하는 write(string $text): string 메서드를 가집니다.
    • content를 비우고 "Content cleared"를 반환하는 clear(): string 메서드를 가집니다.
    • current content를 반환하는 getContent(): string 메서드를 가집니다.
  • Commands.php: Command 및 TextEditor 파일을 포함합니다. Command interface를 Implement하는 두 개의 command class를 Create합니다.
    • WriteCommand: constructor에서 TextEditor와 텍스트 string을 받습니다. execute() 메서드는 editor의 write() 메서드를 calls하고 그 결과를 반환합니다.
    • ClearCommand: constructor에서 TextEditor를 받습니다. execute() 메서드는 editor의 clear() 메서드를 calls하고 그 결과를 반환합니다.
  • main.php: Commands 파일을 포함합니다. 두 개의 입력을 받습니다. 하나는 command type("write" 또는 "clear")이고, 다른 하나는 텍스트 string입니다(write commands에만 사용됨).

    TextEditor instance를 Create합니다. command type을 Based으로 적절한 command 객체를 Create합니다. 그런 다음 command에서 execute()를 calls하고 결과를 출력하는 invoker function 또는 간단한 메커니즘을 Create합니다.

    새 줄에 editor의 current content를 다음 format으로 출력합니다: Content: [content](empty인 경우 공백 뒤에 아무것도 없이 Content:만 출력합니다).

이 challenge는 Command Pattern이 각 작업을 객체로 캡슐화하는 방식을 보여 줍니다. invoker는 write command를 execute하는지 clear command를 execute하는지 알 필요가 없습니다. 단순히 execute()를 calls하고 command가 세부 사항을 처리하도록 합니다.

직접 해보기

<?php

require_once 'Commands.php';

// 입력 읽기
$commandType = trim(fgets(STDIN)); // "write" 또는 "clear"
$text = trim(fgets(STDIN));         // write 명령용 텍스트

// TODO: TextEditor 인스턴스 생성

// TODO: 명령 유형에 따라 적절한 명령 객체 생성
// - "write"인 경우, editor와 text로 WriteCommand 생성
// - "clear"인 경우, editor로 ClearCommand 생성

// TODO: 명령에서 execute()를 호출하는 invoker 메커니즘 생성
// 그리고 결과를 출력

// TODO: 에디터의 현재 내용을 다음 형식으로 출력: "Content: [content]"
// (비어 있으면 공백 뒤에 아무것도 없이 "Content: "만 출력)

?>
quiz icon실력 점검

이 레슨에는 짧은 퀴즈가 포함되어 있습니다. 레슨을 시작해 문제를 풀고 진행 상황을 기록하세요.

객체 지향 프로그래밍의 모든 레슨

직접 연습해 보세요: 온라인 PHP 컴파일러