JAVA의 for-each 순환과 교체에 대한 상세한 설명
1. 교체기 Iterator
인터페이스: Iterator
public interface Iterator<E>{
boolean hasNext();
E next();
void remove();
}
Iterator 인터페이스 API를 보면 콜렉션을 교체하는 교체기임을 알 수 있습니다.교체기는 호출자가 정의된 좋은 의미를 이용하여 교체 기간에 교체기가 가리키는 콜렉션에서 요소를 제거할 수 있도록 합니다.특히 주의해야 할 것은 이 교체기remove () 방법의 사용입니다. 교체기가 가리키는 콜렉션에서 교체기가 되돌아오는 마지막 요소를 제거합니다.매번 넥스트를 호출할 때마다 이 방법을 한 번만 호출할 수 있습니다.만약 교체를 진행할 때 이 방법 (remove 방법) 이외의 다른 방식으로 이 교체기가 가리키는 콜렉션을 수정한다면, 교체기의 행위는 확실하지 않습니다.인터페이스 디자이너는 Iterator
import java.util.ArrayList;
import java.util.Collection;
import java.util.Iterator;
public class ItaratorTest {
public static void main(String[] args) {
Collection<String> list = new ArrayList<String>();
list.add("Android");
list.add("IOS");
list.add("Windows Mobile");
Iterator<String> iterator = list.iterator();
while (iterator.hasNext()) {
String lang = iterator.next();
list.remove(lang);//will throw ConcurrentModificationException
}
}
}
이 코드는 실행할 때 ConcurrentModificationException 이상을 던집니다. 왜냐하면 우리는 교체기가 실행되는 동안iterator의remove () 방법으로 요소를 삭제하지 않고 ArrayList의remove () 방법으로 교체기가 가리키는 collection을 바꾸었기 때문입니다.이것은 교체기의 설계 원칙을 위반하여 이상이 발생했다.보고된 예외 사항은 다음과 같습니다.
Exception in thread "main"java.util.ConcurrentModificationException
at java.util.ArrayList$Itr.checkForComodification(ArrayList.java:859)
at java.util.ArrayList$Itr.next(ArrayList.java:831)
at Text.ItaratorTest.main(ItaratorTest.java:17)
2. for-each 순환과 교체기 Iterator
Java5부터 Java에 for-each 순환이 있어서 콜렉션과array를 순환할 수 있습니다.Foreach 순환은 전통적인 for 순환의 인덱스를 유지하지 않거나iterator/ListIterator (Array List의 일종의 교체기 구현) 를 사용할 때while 순환의hasNext () 방법을 사용하지 않고collection을 반복할 수 있도록 합니다.for-each 순환은 모든 컬렉션이나array의 반복 과정을 간소화합니다.하지만foreach 순환을 사용하는 것도 두 가지 주의해야 한다.
foreach 순환을 사용하는 대상은 Iterable
다음 예제를 참조하십시오.
import java.util.ArrayList;
public class ForeachTest1 {
public static void main(String args[]) {
CustomCollection<String> myCollection = new CustomCollection<String>();
myCollection.add("Java");
myCollection.add("Scala");
myCollection.add("Groovy");
// What does this code will do, print language, throw exception or
// compile time error
for (String language : myCollection) {
System.out.println(language);
}
}
private class CustomCollection<T> {
private ArrayList<T> bucket;
public CustomCollection() {
bucket = new ArrayList();
}
public int size() {
return bucket.size();
}
public boolean isEmpty() {
return bucket.isEmpty();
}
public boolean contains(T o) {
return bucket.contains(o);
}
public boolean add(T e) {
return bucket.add(e);
}
public boolean remove(T o) {
return bucket.remove(o);
}
}
}
상기 코드는 컴파일할 수 없습니다. 이것은 코드 중의 CustomCollection 클래스가 IterableException in thread "main"java.lang.Error: Unresolved compilation problem:
Can only iterate over an array or an instance of java.lang.Iterable
at Text.ForeachTest1.main(ForeachTest1.java:15)
사실상, 컴파일할 때 오류를 발견할 필요가 없습니다. eclipse는 이 코드를 다 쓴 후foreach 순환에 오류를 표시합니다. Can onlyiterate over anarray or an instance of java.lang.Iterable
상기 예시에서 다시 한 번 확인할 수 있는 것은foreach 순환은 Iterable
import java.util.AbstractCollection;
import java.util.ArrayList;
import java.util.Iterator;
public class ForeachTest {
public static void main(String args[]) {
CustomCollection<String> myCollection = new CustomCollection<String>();
myCollection.add("Java");
myCollection.add("Scala");
myCollection.add("Groovy");
for (String language : myCollection) {
System.out.println(language);
}
}
private static class CustomCollection<T> extends AbstractCollection<T> {
private ArrayList<T> bucket;
public CustomCollection() {
bucket = new ArrayList();
}
public int size() {
return bucket.size();
}
public boolean isEmpty() {
return bucket.isEmpty();
}
public boolean contains(Object o) {
return bucket.contains(o);
}
public boolean add(T e) {
return bucket.add(e);
}
public boolean remove(Object o) {
return bucket.remove(o);
}
@Override
public Iterator<T> iterator() {
// TODO Auto-generated method stub
return bucket.iterator();
}
}
}
2. foreach 순환의 내부 실현도 Iterator에 의해 이루어진다foreach 순환이 Iterator를 내부로 사용한다는 사실을 검증하기 위해 우리는 여전히 본고의 첫 번째 실례를 이용하여 검증한다.
public class ItaratorTest {
public static void main(String[] args) {
Collection<String> list = new ArrayList<String>();
list.add("Android");
list.add("IOS");
list.add("Windows Mobile");
// example1
// Iterator<String> iterator = list.iterator();
// while (iterator.hasNext()) {
// String lang = iterator.next();
// list.remove(lang);
// }
// example 2
for (String language : list) {
list.remove(language);
}
}
}
프로그램이 실행될 때 보고된 예외:Exception in thread "main"java.util.ConcurrentModificationException
at java.util.ArrayList$Itr.checkForComodification(ArrayList.java:859)
at java.util.ArrayList$Itr.next(ArrayList.java:831)
at Text.ItaratorTest.main(ItaratorTest.java:22)
이 이상은 for-each 순환 내부에서 Iterator를 사용하여 컬렉션을 훑어보았고, Iterator를 호출했음을 설명합니다.next (), 이것은 (요소의) 변화를 검사하고 ConcurrentModificationException을 던집니다.
요약:
이 내용에 흥미가 있습니까?
현재 기사가 여러분의 문제를 해결하지 못하는 경우 AI 엔진은 머신러닝 분석(스마트 모델이 방금 만들어져 부정확한 경우가 있을 수 있음)을 통해 가장 유사한 기사를 추천합니다:
38. Java의 Leetcode 솔루션텍스트를 자유롭게 공유하거나 복사할 수 있습니다.하지만 이 문서의 URL은 참조 URL로 남겨 두십시오.
CC BY-SA 2.5, CC BY-SA 3.0 및 CC BY-SA 4.0에 따라 라이센스가 부여됩니다.