0Pricing
Clean Architecture & Design Patterns in Practice · 강의

커맨드와 이터레이터 패턴

커맨드로 요청을 객체로 캡슐화하고 이터레이터로 컬렉션을 순회합니다.

커맨드와 이터레이터 패턴은(는) CoddyKit의 무료 Clean Architecture & Design Patterns in Practice 강의입니다. 이것은 4개 중 2번째 강의입니다. 아래에서 전체 강의를 무료로 읽을 수 있으며, 내장 코드 에디터와 24/7 AI 튜터와 함께 브라우저에서 직접 실습할 수 있습니다. 이 강의는 Clean Architecture & Design Patterns in Practice 학습 경로의 일부이며, 진행 상황이 웹과 CoddyKit 앱에 동기화됩니다. Clean Architecture & Design Patterns in Practice 강의에는 총 4개의 강의가 포함되어 있습니다.

이 강의의 일부는 아직 번역되지 않았으며 영어로 표시됩니다.

What is the Command Pattern?

The Command Pattern is a behavioral design pattern that turns a request into a stand-alone object. This object contains all information about the request, including the method to call and the parameters it needs.

Think of it like putting an instruction into a package. You can then pass this package around, queue it, or even undo it later, without the sender needing to know how the instruction is carried out.

Core Components of Command

To understand the Command Pattern, let's look at its key players:

  • Command: An interface or abstract class declaring an execute() method.
  • ConcreteCommand: Implements the Command interface, binding a specific Receiver object to an action.
  • Receiver: The object that performs the actual work. It knows how to carry out the operation.
  • Invoker: Asks the command to carry out its request. It doesn't know the specifics of the operation or the receiver.
  • Client: Creates a ConcreteCommand object and sets its Receiver.

Command Pattern in Action

Let's imagine a smart home system where you want to control a light. Without the Command Pattern, your remote control would directly call light.turnOn() or light.turnOff().

With the Command Pattern, the remote control only knows how to 'execute a command'. It doesn't care if it's turning a light on, opening a garage door, or playing music. This makes your remote control (Invoker) very flexible!

Code: Light On/Off Command

Here's a simple Java example demonstrating the Command Pattern for controlling a light. Notice how the RemoteControl (Invoker) only interacts with the Command interface.

interface Command {
  void execute();
}

class Light {
  public void turnOn() {
    System.out.println("Light is ON");
  }
  public void turnOff() {
    System.out.println("Light is OFF");
  }
}

class LightOnCommand implements Command {
  private Light light;

  public LightOnCommand(Light light) {
    this.light = light;
  }

  @Override
  public void execute() {
    light.turnOn();
  }
}

class LightOffCommand implements Command {
  private Light light;

  public LightOffCommand(Light light) {
    this.light = light;
  }

  @Override
  public void execute() {
    light.turnOff();
  }
}

class RemoteControl {
  private Command command;

  public void setCommand(Command command) {
    this.command = command;
  }

  public void pressButton() {
    command.execute();
  }
}

public class Main {
  public static void main(String[] args) {
    Light livingRoomLight = new Light();

    LightOnCommand onCommand = new LightOnCommand(livingRoomLight);
    LightOffCommand offCommand = new LightOffCommand(livingRoomLight);

    RemoteControl remote = new RemoteControl();

    remote.setCommand(onCommand);
    remote.pressButton();

    remote.setCommand(offCommand);
    remote.pressButton();
  }
}

Benefits of Command Pattern

The Command Pattern offers several powerful advantages:

  • Decoupling: The invoker is decoupled from the receiver, reducing dependencies.
  • Undo/Redo: Commands can be stored in a history list, making undo/redo functionality easier to implement.
  • Queuing/Logging: Requests can be queued, logged, and executed at different times.
  • Extensibility: Adding new commands doesn't require changing existing invoker code.

What is the Iterator Pattern?

The Iterator Pattern is a behavioral design pattern that provides a way to access the elements of an aggregate object (like a list or array) sequentially without exposing its underlying representation.

Imagine you have a playlist of songs. An iterator allows you to go through each song one by one (next, previous, etc.) without needing to know if the playlist is stored as an array, a linked list, or something else entirely.

Core Components of Iterator

The Iterator Pattern involves these main components:

  • Iterator: An interface defining methods for accessing and traversing elements (e.g., hasNext(), next()).
  • ConcreteIterator: Implements the Iterator interface, keeping track of the current position in the traversal.
  • Aggregate: An interface or abstract class defining a method for creating an Iterator object (e.g., createIterator()).
  • ConcreteAggregate: Implements the Aggregate interface and returns an instance of a ConcreteIterator.

Iterator Pattern in Action

Most programming languages have built-in iterators (like Java's Iterator or Python's iterables). But sometimes, you build a custom collection where you need to define your own traversal logic.

For example, if you have a custom MyStringList class that stores strings internally, an iterator would allow external code to loop through these strings without knowing if MyStringList uses an array, a linked list, or a tree structure internally.

Code: Custom List Iterator

This Java example shows how to create a custom StringList and an Iterator for it. The Main method can iterate through the list using the iterator without knowing its internal array.

interface MyIterator {
  boolean hasNext();
  String next();
}

interface MyAggregate {
  MyIterator createIterator();
}

class MyStringList implements MyAggregate {
  private String[] items;
  private int count;

  public MyStringList(int capacity) {
    items = new String[capacity];
    count = 0;
  }

  public void add(String item) {
    if (count < items.length) {
      items[count++] = item;
    }
  }

  @Override
  public MyIterator createIterator() {
    return new StringListIterator(this);
  }

  // Helper to access elements by index for the iterator
  public String get(int index) {
    if (index >= 0 && index < count) {
      return items[index];
    }
    return null;
  }

  public int size() {
    return count;
  }
}

class StringListIterator implements MyIterator {
  private MyStringList list;
  private int position;

  public StringListIterator(MyStringList list) {
    this.list = list;
    this.position = 0;
  }

  @Override
  public boolean hasNext() {
    return position < list.size();
  }

  @Override
  public String next() {
    if (hasNext()) {
      return list.get(position++);
    }
    return null;
  }
}

public class Main {
  public static void main(String[] args) {
    MyStringList names = new MyStringList(5);
    names.add("Alice");
    names.add("Bob");
    names.add("Charlie");

    MyIterator iterator = names.createIterator();

    System.out.println("Iterating through names:");
    while (iterator.hasNext()) {
      System.out.println(iterator.next());
    }
  }
}

Quick Check: Design Patterns

You've learned about two powerful behavioral patterns. Let's test your understanding.

Recap: Command & Iterator

Great job! In this lesson, we explored two essential behavioral design patterns:

  • The Command Pattern encapsulates a request as an object, enabling powerful features like undo/redo, queuing, and logging requests, while decoupling the invoker from the receiver.
  • The Iterator Pattern provides a standardized way to traverse elements in a collection, abstracting away the collection's internal structure and promoting flexible iteration methods.

Mastering these patterns will significantly improve the flexibility and maintainability of your software designs.

자주 묻는 질문

“커맨드와 이터레이터 패턴” 강의는 무료인가요?

네 — “커맨드와 이터레이터 패턴” 전체 내용을 이 웹사이트에서 무료로 읽을 수 있습니다. 인터랙티브하게 실습하려면(내장 코드 에디터와 24/7 AI 튜터), CoddyKit PRO로 업그레이드하면 Clean Architecture & Design Patterns in Practice 강의 전체를 잠금 해제할 수 있습니다. Clean Architecture & Design Patterns in Practice 강의에는 총 4개의 강의가 포함되어 있습니다.

“커맨드와 이터레이터 패턴”에서 뭘 배우나요?

커맨드로 요청을 객체로 캡슐화하고 이터레이터로 컬렉션을 순회합니다. 브라우저에서 직접 실행하는 실습 코드로 Clean Architecture & Design Patterns in Practice을(를) 배우며, 24/7 AI 튜터가 강의를 진행하면서 질문에 답변해줍니다.

Clean Architecture & Design Patterns in Practice을(를) 시작하는 데 경험이 필요한가요?

사전 경험은 필요하지 않습니다. CoddyKit의 Clean Architecture & Design Patterns in Practice은(는) 초급자부터 고급 학습자까지를 위해 구성되어 있으므로, 여기서 시작하거나 처음부터 시작할 수 있으며 자신의 속도대로 진행할 수 있습니다. 이것은 4개 중 2번째 강의입니다.

“커맨드와 이터레이터 패턴” 강의는 얼마나 걸리나요?

대부분의 CoddyKit 강의는 약 5~10분이 소요됩니다. 각 강의는 간결하고 인터랙티브하여 꾸준한 진행이 가능하며, 웹과 앱에서 중단한 부분부터 바로 시작할 수 있습니다.

이 Clean Architecture & Design Patterns in Practice 강의에서 코드를 작성하고 실행할 수 있나요?

네. 모든 Clean Architecture & Design Patterns in Practice 강의에는 내장 코드 에디터가 포함되어 있으므로, 브라우저에서 바로 실제 코드를 작성하고 실행한 후 즉시 AI 피드백을 받을 수 있습니다 — 로컬 설정이 필요 없습니다.

이 강의의 모든 강의

  1. 옵서버와 전략 패턴
  2. 커맨드와 이터레이터 패턴
  3. 템플릿 메서드와 상태 패턴
  4. Mediator와 Chain of Responsibility
← Clean Architecture & Design Patterns in Practice(으)로 돌아가기