본문 바로가기

코딩/Software Architecture

[GoF Design Pattern] Chain of Responsibility

* Chain of Responsibility Pattern

Chain of Responsibility : 여러 개의 책임들을 동적으로 (실행 중) 연결해서 순차적으로 실행하는 패턴

                                          기능을 클래스 별로 분리 후 구련 해 코드가 최적화됨.

책임 : 무언가를 처리하는 기능

예시 : URL -> 책임 1(프로토콜) -> 책임 2(도메인) -> 책임 3(포트)

          신용카드 -> 책임 1(국민카드) -> 책임 2(신한카드) -> 책임 3(삼성카드)  카드 회사 찾기.

책임들 사이에 연결이 필요하므로 Handler는 자신과 동일한 객체를 필드로 가짐.

Handler : 책임에 대한 부모 클래스. 이 클래스를 상속받아 구체적인 기능에 대한 책임을 구현함.

ProtocolHandler : URL에서 protocol 처리. 나머지 클래스도 이름에 따라 처리.

public abstract class Handler {
    protected Handler nextHandler = null;
    
    public Handler setNect(Handler handler) {
    	this.nextHandler = handler;
        return handler;
    }
    
    protected abstract void process(String url); // 구체적인 기능에 대한 책임
    
    public void run(String url) {  // 연결된 책임을 순차적으로 실행
    	process(url);
        if(nextHandler != null) nextHandler.run(url);
    }
}

각 책임을 수행하는 Handler 를 구체화한 객체들

 

public class ProtocolHandler extends Handler {
    
    @Override
    protected void process(String url) {
    	int index = url.indexOf("://");
        if(index != -1) {
        	System.out.println("PROTOCOL: " + url.subString(0, index));
        } else {
        	System.out.println("NO PROTOCOL");
        }
    }
}

 - DomainHandler

public class DomainHandler extends Handler {
    
    @Override
    protected void process(String url) {
    	int startIndex = url.indexOf("://");
        int lastIndex = url.lastIndexOf(":");
        
        System.out.print("DOMAIN: ");
        if(startIndex == -1) {
        	if(lastIndex == -1) {
            	System.out.println(url);
            } else {
            	System.out.println(url.substring(0, lastIndex));
            }
        } else if(startIndex != lastIndex) {
        	System.out.println(url.substring(startIndex+3, lastIndex));
        } else if(startIndex == lastIndex) {
        	System.out.println(url.substring(startIndex+3));
        } else {
        	System.out.println("NONE");
        }
    }
}

 - PortHandler

public class PortHandler extends Handler {

    @Override
    protected void process(String url) {
    	int index = url.lastIndexOf(":");
        if(index != -1) {
        	String strPort = url.substring(index+1);
            try {
            	int port = Integer.parseInt(strPort);
                System.out.println("PORT: " + prot);
                return;
            } catch (NumberFprmatException e) {
             	e.printStackTace();
            }
        }
     	System.out.println("NO PORT");
    }
}

구현한 클래스를 활용.

public static void main(String[] args) {
    Handler handler1 = new ProtocolHandler();
    Handler handler2 = new PortHandler();
    Handler handler3 = new DomainHandler();
    
    handler1.setNext(handler2).setNext(handler3); // 연속적인 책임 고리를 만듦
    
    String url = "http://www.youtube.com:1004";
    System.out.println("INPUT: " + url);
    
    handler1.run(url); // 최종 실행
}

만약 새로운 기능 (책임) 이 필요하다면 해당 클래스를 추가해 사용 가능. 다른 클래스는 변경 X

'코딩 > Software Architecture' 카테고리의 다른 글

[GoF Design Pattern] Abstract Factory  (0) 2022.12.24
[Design Pattern] GRASP Pattern  (0) 2022.12.10
[GoF Design Pattern] Mediator  (0) 2022.12.06
[GoF Design Pattern] Decorator  (0) 2022.12.05
[GoF Design Pattern] Memento  (0) 2022.12.05