헤드 퍼스트 디자인 패턴 | 에릭 프리먼 | 한빛미디어- 교보ebook

14가지 GoF 필살 패턴!, 경력과 세대를 넘어 오랫동안 객체지향 개발자의 성장을 도와준 디자인 패턴 교과서의 화려한 귀환! 》 2005년부터 디자인 패턴 도서 분야 부동의 1위 》 디자인 패턴의 고

ebook-product.kyobobook.co.kr

서로 다는 방식으로 저장한 것을 공통으로 다루고 싶다.

import java.util.*;
import java.util.Map.Entry;
import java.util.function.Supplier;
import java.util.stream.Collectors;
import java.util.stream.IntStream;

public class IteratorTest {
	static Supplier<IntStream> supply(){
		return ()-> new Random().ints(10, 1, 100);
	}
	
	static class ClassArr<E> implements Iterable<E>{
		E[] dataArr;
		
		public ClassArr(E[] dataArr) {
			this.dataArr = (E[]) dataArr;
		}

		@Override
		public Iterator<E> iterator() {
			return new Iterator<E>() {
				int cursor = 0;
				public boolean hasNext() {
					return cursor < dataArr.length;
				}
				public E next() {
					return dataArr[cursor++];
				}
			};
		}
		
	}
	
	static class MapClass implements Iterable<Map.Entry<Object, List<Integer>>>{
		Map<Object, List<Integer>> map = new HashMap<>();

		public MapClass() {
			map= supply().get().boxed().collect(Collectors.groupingBy(n->n));
		}
		
		@Override
		public Iterator<Entry<Object, List<Integer>>> iterator() {
			return map.entrySet().iterator();
		}

	}

	
	static class ArrClass implements Iterable<Integer>{
		int[] intArr = supply().get().toArray();

		@Override
		public Iterator<Integer> iterator() {
			return new Iterator<Integer>() {
				int cursor = 0;
				public Integer next() {
					return intArr[cursor++];
				}
				public boolean hasNext() {
					return cursor<intArr.length;
				}
			};
		}
	}
	static class ListClass implements Iterable<Integer>{
		List<Integer> intList = supply().get().boxed().toList();
		@Override
		public Iterator<Integer> iterator() {
			return intList.iterator();
		}
		
	}
	
	public static void main(String[] args) {
		String[] test = {"배열은","향상된","반복문","사용가능"};
		//배열 향상 포문 가능
		for(String data : test) {
			System.out.print(data+" ");
		}
		System.out.println();
		//어떠한 클래스도 Iterable만 알맞게 구현하면 전부 향상 포문 가능하다.
		for(String data : new ClassArr<>(test)) {
			System.out.print(data+" ");
		}
		System.out.println();
		for(Integer val : new ArrClass()) {
			System.out.print(val+" ");
		}
		System.out.println();
		for(Integer val :new ListClass()) {
			System.out.print(val+" ");
		}
		System.out.println();
		for(Entry en : new MapClass()) {
			System.out.print(en + " ");
		}
	}
}
배열은 향상된 반복문 사용가능 
배열은 향상된 반복문 사용가능 
61 13 57 51 30 49 25 5 48 48 
34 91 69 72 70 1 18 5 26 55 
49=[49] 17=[17] 97=[97] 35=[35] 52=[52] 53=[53] 56=[56] 40=[40] 45=[45] 15=[15]

반복자 패턴 알아보기

반복자 패턴은 Iterator 인터페이스에 의존한다

인터페이스만 있으면 배열, 리스트, 해시테이블 모든 컬렉션을 순회할 있다.

반복자 패턴의 정의

집합체 내에서 어떤 식으로 일이 처리되는지 전혀 모르는 상태에서 안에 들어있는 모든 항목을 대상으로 반복 작업을 수행할 있다.

 

또한 서로 다른 종류의 집합체라도 Iterator 구현해 리턴하면 같은 방법으로 순회를 있다.

집합체는 요소 순회만 Iterator에게 위임하고, 내부 자료구조 관리만 잘하면 된다.

컴포지트 패턴의 정의

반복자 패턴만으론 처리하기 어려워 메뉴 관리에 도움되는 컴포지트 패턴 도임

객체를 트리구조로 구성해서 부분-전체 계층구조를 구현한다. 컴포지트 패턴을 사용하면 클라이언트에서 개별 객체와 복합 객체를 똑같은 방법으로 다룰 수 있다.

 

import java.util.ArrayList;
import java.util.List;

public class CompositeTest {
	//구성요소
	static abstract class MenuComponent{
		public void add(MenuComponent menuComponent) {
			throw new UnsupportedOperationException();
		}
		public void remove(MenuComponent menuComponent) {
			throw new UnsupportedOperationException();
		}
		public MenuComponent getChild(int i) {
			throw new UnsupportedOperationException();
		}
		public String getName() {
			throw new UnsupportedOperationException();
		}
		public String getDescription() {
			throw new UnsupportedOperationException();
		}
		public double getPrice() {
			throw new UnsupportedOperationException();
		}
		public boolean isVegetarian() {
			throw new UnsupportedOperationException();
		}
		public void print() {
			throw new UnsupportedOperationException();
		}
	}
	//잎
	static class MenuItem extends MenuComponent{
		String name;
		String description;
		boolean vegetarian;
		double price;
		
		public MenuItem(String name, String description, boolean vegetarian, double price) {
			this.name = name;
			this.description = description;
			this.vegetarian = vegetarian;
			this.price = price;
		}
		
		public String getName() {
			return name;
		}
		
		public String getDescription() {
			return description;
		}
		
		public boolean isVegetarian() {
			return vegetarian;
		}
		
		public double getPrice() {
			return price;
		}
		
		public void print() {
			System.out.print("  "+getName());
			if(isVegetarian()) {
				System.out.print("(v)");
			}
			System.out.println(", "+getPrice());
			System.out.println("    -- "+getDescription());
		}
		
	}
	//노드
	static class Menu extends MenuComponent{
		List<MenuComponent> menuComponents = new ArrayList<>();
		String name;
		String description;
		
		public Menu(String name, String description) {
			this.name = name;
			this.description = description;
		}
		
		public void add(MenuComponent menuComponent) {
			menuComponents.add(menuComponent);
		}
		public void remove(MenuComponent menuComponent) {
			menuComponents.remove(menuComponent);
		}
		public MenuComponent getChild(int i) {
			return menuComponents.get(i);
		}
		
		public String getName() {
			return name;
		}
		public String getDescription() {
			return description;
		}
		
		public void print() {
			System.out.print("\n"+getName());
			System.out.println(", "+getDescription());
			System.out.println("----------------------");
			
			for(MenuComponent menuComponent : menuComponents) {
				menuComponent.print();
			}
			
		}
	}
	
	static class Waitress{
		MenuComponent allmenus;

		public Waitress(MenuComponent allmenus) {
			this.allmenus = allmenus;
		}
		
		public void printMenu() {
			allmenus.print();
		}
	}
	
	
	public static void main(String[] args) {
		MenuComponent phMenu = new Menu("팬케이크 하우스 메뉴", "아침 메뉴");
		MenuComponent dinerMenu = new Menu("객체마을 식당 메뉴", "점심 메뉴");
		MenuComponent cafeMenu = new Menu("카페 메뉴", "저녁 메뉴");
		MenuComponent dessertMenu = new Menu("디저트 메뉴", "디저트를 즐겨 보에쇼");
		
		MenuComponent allMenu = new Menu("전체 메뉴", "전체 메뉴");
		
		allMenu.add(phMenu);
		allMenu.add(dinerMenu);
		allMenu.add(cafeMenu);
		
		phMenu.add(
				new MenuItem("K&B 팬케이크 아침정식"
				,"팬케이크에 스크램블에그와 토스트", true, 2.99));
		phMenu.add(
				new MenuItem("레귤러 팬케이크 아침정식"
				,"팬케이크에 계란 후라이와 소세지", false, 2.99));
		phMenu.add(
				new MenuItem("블루베리 팬케이크"
				,"팬케이크와 블루베리, 블루베리 시럽", true, 3.49));
		phMenu.add(
				new MenuItem("와플"
				,"와플과 블루베리 또는 딸기를 드립니다.", true, 3.59));
		
		dinerMenu.add(
				new MenuItem("채식주의자용 BLT"
				, "통밀 위에 콩고기 베이컨, 상추, 토마토를 얹은 메뉴", true, 2.99));
		
		dinerMenu.add(
				new MenuItem("BLT"
				, "통밀 위에 베이컨, 상추, 토마토를 얹은 메뉴", false, 2.99));
		dinerMenu.add(
				new MenuItem("오늘의 스프"
				, "감자 샐러드를 곁들인 오늘의 스프", true, 2.99));
		dinerMenu.add(
				new MenuItem("핫도그"
				, "사워크라우트, 갖은 양념, 양파, 치즈가 곁들여진 핫도그", true, 2.99));
		dinerMenu.add(
				new MenuItem("파스타"
				, "마리나라 소스 스파게티, 효모빵도 드립니다.", true, 3.89));
		dinerMenu.add(dessertMenu);
		
		
		dessertMenu.add(
				new MenuItem("애플 파이"
				, "바삭바삭한 크러스트에 바닐라 아이스크림이 얹혀 있는 애플 파이", true, 1.59));
		dessertMenu.add(
				new MenuItem("치즈케이크"
				, "초콜릿 그레이엄 크러스트 위에 부드러운 뉴욕 치즈케이크", true, 1.99));
		dessertMenu.add(
				new MenuItem("소르베"
				, "라스베리와 라임의 절묘한 조화", true, 1.89));
		
		cafeMenu.add(
				new MenuItem("베지 버거와 에어 프라이"
				, "통밀빵, 상추, 토마토, 감자 튀김이 첨가된 베지 버거", true, 1.59));
		cafeMenu.add(
				new MenuItem("오늘의 스프"
				, "통밀빵, 상추, 토마토, 감자 튀김이 첨가된 베지 버거", false, 0.69));
		cafeMenu.add(
				new MenuItem("투리토"
				, "통 핀토콩과 살사, 구아카몰이 곁들여진 푸짐한 부리토", true, 0.89));
		
		Waitress waitress = new Waitress(allMenu);
		waitress.printMenu();
	}
}
전체 메뉴, 전체 메뉴
----------------------

팬케이크 하우스 메뉴, 아침 메뉴
----------------------
  K&B 팬케이크 아침정식(v), 2.99
    -- 팬케이크에 스크램블에그와 토스트
  레귤러 팬케이크 아침정식, 2.99
    -- 팬케이크에 계란 후라이와 소세지
  블루베리 팬케이크(v), 3.49
    -- 팬케이크와 블루베리, 블루베리 시럽
  와플(v), 3.59
    -- 와플과 블루베리 또는 딸기를 드립니다.

객체마을 식당 메뉴, 점심 메뉴
----------------------
  채식주의자용 BLT(v), 2.99
    -- 통밀 위에 콩고기 베이컨, 상추, 토마토를 얹은 메뉴
  BLT, 2.99
    -- 통밀 위에 베이컨, 상추, 토마토를 얹은 메뉴
  오늘의 스프(v), 2.99
    -- 감자 샐러드를 곁들인 오늘의 스프
  핫도그(v), 2.99
    -- 사워크라우트, 갖은 양념, 양파, 치즈가 곁들여진 핫도그
  파스타(v), 3.89
    -- 마리나라 소스 스파게티, 효모빵도 드립니다.

디저트 메뉴, 디저트를 즐겨 보에쇼
----------------------
  애플 파이(v), 1.59
    -- 바삭바삭한 크러스트에 바닐라 아이스크림이 얹혀 있는 애플 파이
  치즈케이크(v), 1.99
    -- 초콜릿 그레이엄 크러스트 위에 부드러운 뉴욕 치즈케이크
  소르베(v), 1.89
    -- 라스베리와 라임의 절묘한 조화

카페 메뉴, 저녁 메뉴
----------------------
  베지 버거와 에어 프라이(v), 1.59
    -- 통밀빵, 상추, 토마토, 감자 튀김이 첨가된 베지 버거
  오늘의 스프, 0.69
    -- 통밀빵, 상추, 토마토, 감자 튀김이 첨가된 베지 버거
  투리토(v), 0.89
    -- 통 핀토콩과 살사, 구아카몰이 곁들여진 푸짐한 부리토

 

 

+ Recent posts