[Spring] 다형성, 디자인패턴(Factory 패턴)을 이용 -> 제어의 역행 & 결합도 낮추기

2021. 3. 28. 02:53웹 개발/JAVA

<서블릿 컨테이너 작동순서>

 

1. WEB-INF/web.xml 파일을 로딩하여 구동

2. 브라우저로부터 /hello.do 요청 수신

3. web.xml에서 패키지명.클래스명(ex: com.springbook.biz.HelloServlet) 을 찾아 객체를 생성하고 doGet() 메소드 호출

  <servlet>
    <servlet-name>hello</servlet-name>
    <servlet-class>com.springbook.biz.HelloServlet</servlet-class>
  </servlet>
  <servlet-mapping>
    <servlet-name>hello</servlet-name>
    <url-pattern>/hello.do</url-pattern>
  </servlet-mapping>
public class HelloServlet extends HttpServlet{
	public HelloServlet() {
		System.out.println("===> HelloServlet 객체생성");
	}
	
	protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException{
		System.out.println("===> doGet() 메소드 호출");
	}
}

4. doGet() 메소드 실행 결과를 클라이언트 브라우저로 전송 

 

 

<제어의 역행과 결합도>

 

제어의 역행은 결합도와 관련된 개념으로 이해가능.

[결합도]하나의 클래스가 다른 클래스와 얼마나 많이 연결되어 있는지를 나타내는 표현. 

결합도가 높은 프로그램은 유지보수가 어려움

 

기존에 자바 기반으로 애플리케이션 개발할 때, 객체를 생성하고 객체들 사이의 의존관계를 처리하는 것에 대한 책임은 전적으로 개발자에게 있었음. 

즉, 개발자가 어떤 객체를 생성할지 판단하고 객체 간의 의존관계 역시 소스코드로 표현해야 했음

 

하지만 [제어의 역행]이라는 것은 이런 일련의 작업들을 소스코드로 처리하지 않고 컨테이너로 처리하는 것을 의미

따라서 제어의 역행을 이용하면 소스에서 객체 생성과 의존관계에 대한 코드가 사라져 결과적으로 낮은 결합도의 컴포넌트를 구현할 수 있게 함. 

 

 

<결합도가 높은 프로그램>

 

1. 인터페이스를 통한 다형성을 이용하지 않기 때문에 유지보수시 메서드명이 다르게 사용됨.

따라서 관련 메서드명을 모두 일일이 교체해야하는 불편함 발생  

 

2.  디자인 패턴(ex. Factory 패턴) 이용하지 않을 경우, 사용할 객체를 생성하는 소스를 일일이 수정해줘야만 함. 

- ex) SamsungTV tv = new SamsungTV();

 

 

<다형성 이용하기>

 

결합도를 낮추는 방법으로 객체지향 언어의 핵심 개념인 다형성(Polymorphism)을 이용하는 것.

 

public class SamsungTV implements TV {

	@Override
	public void powerOn() {
		System.out.println("SamsungTV---전원 켠다.");
	}

	@Override
	public void powerOff() {
		System.out.println("SamsungTV---전원 끈다.");
	}

	@Override
	public void volumeUp() {
		System.out.println("SamsungTV---소리 올린다.");	
	}

	@Override
	public void volumeDown() {
		System.out.println("SamsungTV---소리 내린다.");
	}
}
public class LgTV implements TV {

	@Override
	public void powerOn() { 
		System.out.println("LgTV---전원 켠다.");
	}

	@Override
	public void powerOff() {
		System.out.println("LgTV---전원 끈다.");
	}

	@Override
	public void volumeUp() {
		System.out.println("LgTV---소리 올린다.");
	}

	@Override
	public void volumeDown() {
		System.out.println("LgTV---소리 내린다.");
	}
}	
public class TVUser {

	public static void main(String[] args) {
		
		
		TV tv = new LgTV(); // 삼성TV로 변경하고싶을 경우, TV TV = new SamsungTV();로만 수정해주면 됨 
		tv.powerOn();
		tv.volumeUp();
		tv.volumeDown();
		tv.powerOff();
		
	}
}

 

 

<디자인 패턴 이용하기>

Factory패턴을 적용하면 유지보수시 객체생성 코드가 적힌 소스를 일일이 찾아다니면서 교체해줘야하는 불편함 해소됨 

public class BeanFactory {
	public Object getBean(String beanName) {
		if(("samsung").equals(beanName)) {
			return new SamsungTV();
		} else if(("lg").equals(beanName)) {
			return new LgTV();
		}
		return null;
	}
}
public class TVUser {

	public static void main(String[] args) {
		
		//디자인 패턴(Factory 패턴) 적용
		BeanFactory factory = new BeanFactory(); 
		TV tv = (TV) factory.getBean(args[0]); //소스수정 없이도 원하는 객체를 생성할 수 있게 됨 
		
        
                tv.powerOn();
		tv.volumeUp();
		tv.volumeDown();
		tv.powerOff();	
    }
 }

 

 

출처:  채규태, 『SPRING QUICK START, 루비페이퍼(2018), p36~47.

'웹 개발 > JAVA' 카테고리의 다른 글

[객체지향] 정보의 은닉(Information Hiding)  (0) 2021.04.11