Programming/Refactoring

리팩토링 - 메소드 올리기 (Pull up method)

JaeHoney 2022. 2. 20. 19:51

메소드 올리기 (Pull up method)

메소드 올리기는 하위 클래스들의 중복 메소드를 상위 클래스로 빼는 리팩토링 기술입니다.

 

아래와 같은 Dashboard 클래스가 있고, 이를 상속하는 두 클래스가 있다고 가정하겠습니다.

 

[부모 클래스]

public class Dashboard {

    public static void main(String[] args) throws IOException {
        ReviewerDashboard reviewerDashboard = new ReviewerDashboard();
        reviewerDashboard.printReviewers();

        ParticipantDashboard participantDashboard = new ParticipantDashboard();
        participantDashboard.printParticipants(15);
    }
    
}

[자식 클래스]

public class ParticipantDashboard extends Dashboard {

    public void printParticipants(int eventId) throws IOException {
        // Get github issue to check homework
        GitHub gitHub = GitHub.connect();
        GHRepository repository = gitHub.getRepository("whiteship/live-study");
        GHIssue issue = repository.getIssue(eventId);

        // Get participants
        Set<String> participants = new HashSet<>();
        issue.getComments().forEach(c -> participants.add(c.getUserName()));

        // Print participants
        participants.forEach(System.out::println);
    }

}
public class ReviewerDashboard extends Dashboard {

    public void printReviewers() throws IOException {
        // Get github issue to check homework
        Set<String> reviewers = new HashSet<>();
        GitHub gitHub = GitHub.connect();
        GHRepository repository = gitHub.getRepository("whiteship/live-study");
        GHIssue issue = repository.getIssue(30);

        // Get reviewers
        issue.getComments().forEach(c -> reviewers.add(c.getUserName()));

        // Print reviewers
        reviewers.forEach(System.out::println);
    }

}

사실 잘 보시면, 자식 클래스들의 코드는 꽤 비슷한 코드입니다.

 

만약, 해당 기능에 대한 인터페이스가 변경되거나 하는 변경사항을 적용하려면 자식 클래스들의 메서드를 전부 수정해야 합니다.

 

따라서, 부모 클래스로 해당 로직을 올려줘야 합니다.

 

<참고> IDE가 제공하는 Pull Members Up을 사용하면 해당 메서드를 상위 메서드로 올릴 수 있습니다.

 

결과

<부모 클래스>

public class Dashboard {

    public static void main(String[] args) throws IOException {
        ReviewerDashboard reviewerDashboard = new ReviewerDashboard();
        reviewerDashboard.printReviewers();

        ParticipantDashboard participantDashboard = new ParticipantDashboard();
        participantDashboard.printUsernames(15);
    }

    public void printUsernames(int eventId) throws IOException {
        // Get github issue to check homework
        GitHub gitHub = GitHub.connect();
        GHRepository repository = gitHub.getRepository("whiteship/live-study");
        GHIssue issue = repository.getIssue(eventId);

        // Get participants
        Set<String> participants = new HashSet<>();
        issue.getComments().forEach(c -> participants.add(c.getUserName()));

        // Print participants
        participants.forEach(System.out::println);
    }
}

<자식 클래스>

public class ParticipantDashboard extends Dashboard {

}
public class ReviewerDashboard extends Dashboard {

    public void printReviewers() throws IOException {
        super.printUsernames(30);
    }

}

 

이렇게 자식 클래스의 공동 메소드를 발견했고, 그 공동 메소드를 상위 클래스의 메소드로 올리고, 상위 클래스의 메소드를 호출하는 식으로 변경했습니다.

 

따라서 로직의 변경이 일어났을 떄 상속을 이용해서 상위 클래스만 수정해주면 되는 결과를 얻을 수 있습니다. 

 

감사합니다.


 

출처 : 코딩으로 학습하는 리팩토링 - 인프런 백기선님 강의
 

코딩으로 학습하는 리팩토링 - 인프런 | 강의

리팩토링은 소프트웨어 엔지니어가 갖춰야 할 기본적인 소양 중 하나입니다. 이 강의는 인텔리J와 자바를 사용하여 보다 실용적인 방법으로 다양한 코드의 냄새와 리팩토링 기술을 설명하고 직

www.inflearn.com