## 25. Iterator 디자인 패턴을 활용하여 목록 조회 기능을 캡슐화하기
- GoF의 디자인 패턴 중 Iterator 패턴의 동작원리 이해 및 구현
- ArrayList, LinkedList, Stack, Queue에 적용
- 중접 클래스 문법을 이용하여 Iterator 구현하기
- static/non-static nested 클래스 문법을 활용하는 방법
- local/anonymous 클래스 문법을 활용하는 방법
ㄴ bitcamp.util 패키지에 Iterator 인터페이스 생성
Iterator.java
ㄴ Iterator 인터페이스에 제네릭 E 추가
ㄴ hasNext() 는 값을 꺼내기 전에 꺼낼 값이 있는지 확인할 때 호출함
ㄴ E next() 는 목록에서 값을 꺼내는 코드
ㄴ bitcamp.util 패키지에 ListIterator 클래스 생성
ListIterator.java
ListIterator.java
ㄴ ListIterator 클래스에 제네릭 E 추가
ListIterator.java
=>
ListIterator.java
=>
ListIterator.java
=>
=>
ListIterator.java
ㄴ cursor 변수의 값이 목록의 크기보다 작으면 다음 요소가 있는 것으로 판단
ㄴ 다음 요소를 반환하고 cursor 변수를 1 증가시킴
=> list.get(cursor++)를 통해 현재 인덱스의 값을 가져옴
ArrayList.java
ㄴ ListIterator 객체를 생성할 때 this를 인자로 전달하여 현재 List 객체에 대한 참조를 전달
ArrayList.java
ㄴ iterator() 메서드는 Iterator 객체를 반환하며, 해당 객체는 List의 요소를 순차적으로 접근 가능
=>
ArrayList.java
ㄴ 굳이 변수 사용할 필요 없음
List.java
ㄴ Iterator 인터페이스를 List 인터페이스에 추가
ArrayList.java
ㄴ @Override 어노테이션으로 컴파일러가 해당 메서드가 실제로 슈퍼클래스나 인터페이스의 메서드를 재정의하는지 검사하여 오류를 방지함
MemberListListener.java
MemberListListener.java
=>
MemberListListener.java
LinkedList.java
=>
ㄴ iterator() 오버라이딩
MemberListListener.java
ㄴ 여기서 iterator 는 목록에서 데이터를 대신 꺼내주는 객체를 얻도록 해줌
ㄴ iterator 이용 시 for 문 제거 후 while 문으로 대체
ㄴ AbstractList 클래스 생성
AbstractList.java
ㄴ 위에서 LinkedList.java 에 재정의한 iterator() 잘라내오기
AbstractList.java
ㄴ LinkedList 에 선언되어있는 size 를 AbstractList 클래스로 가져오기
AbstractList.java
ㄴ AbstractList 클래스 추상화 -> abstract
AbstractList.java
ㄴ LinkedList 클래스에서 size() 메서드를 잘라내옴
AbstractList.java
ㄴ LinkedList 클래스에서 isValid(int index) 메서드를 잘라내옴
=>
AbstractList.java
ㄴ 접근 범위 늘려줌
LinkedList.java
ㄴ AbstractList 클래스를 상속하도록 수정해줌
ArrayList.java
ㄴ length -> size 로 Rename
ArrayList.java
ㄴ 해당 코드 제거
BoardListListener.java
ㄴ Iterator 객체를 통해 hasNext() 메서드를 호출하여 다음 데이터가 있는지 확인하고, next() 메서드를 호출하여 다음 데이터를 가져옴
1. top level class - ListIterator
AbstractList.java
ㄴ ListIterator 클래스 복사해서 AbstractList 클래스 안에 넣기
ㄴ 클래스 앞에 static 붙여주기
2. static nested class - ListIterator2
AbstractList.java
3. non-static nested class - ListIterator3
AbstractList.java
AbstractList.java
4. static nested class - ListIterator4
AbstractList.java
5. anonymous class - 이름 없음
AbstractList.java
ㄴ AbstractList 클래스의 iterator() 메서드에서 익명 클래스를 사용하여 Iterator 객체를 생성하는 방법
ㄴ 익명 클래스는 클래스 이름이 없고, 바로 인스턴스를 생성하면서 구현을 정의하는 방식
ㄴ 익명 클래스는 주로 한 번만 사용되는 간단한 구현체를 만들 때 유용
ㄴ 위의 코드에서는 Iterator<E> 인터페이스를 구현하는 익명 클래스를 생성하고 있음
ㄴ 익명 클래스 내부에는 cursor라는 정수형 변수가 선언되어 있으며, hasNext()와 next() 메서드가 구현되어 있음
ㄴ hasNext() 메서드는 현재 cursor 값이 AbstractList의 크기보다 작은지를 확인하여 다음 요소의 존재 여부를 판단
ㄴ next() 메서드는 현재 cursor 값에 해당하는 AbstractList의 요소를 반환하고, cursor 값을 1 증가시킴
=> 이렇게 익명 클래스를 사용하여 Iterator 객체를 생성하면 AbstractList의 인스턴스 주소를 받아 생성된 익명 클래스의 인스턴스 내부에서 사용할 수 있음
Stack에 적용
Stack.java
ㄴ Stack 클래스에서 iterator() 오버라이딩
Stack.java
Stack.java
Stack.java
Stack.java
=>
Stack.java
Stack.java
Queue 에 적용
Queue.java
Queue.java
Queue.java
Queue.java
Queue.java
Queue.java
BreadCrumbPrompt.java