2008-08-26 5 views
57

В Java 5 и выше у вас есть цикл Еогеасп, который работает волшебно на что-либо, реализующего Iterable:Почему нет перечислений Iterable?

for (Object o : list) { 
    doStuff(o); 
} 

Однако Enumerable до сих пор не реализует Iterable, а это означает, что перебирать в Enumeration вы должны сделать следующее :

for(; e.hasMoreElements() ;) { 
    doStuff(e.nextElement()); 
} 

кто-нибудь знает, если есть причина, почему Enumeration до сих пор не реализует Iterable?

Edit: В разъяснении, я не говорю о концепции языковой с enum, я говорю с Java-определенный класс в Java API под названием «Enumeration».

+0

Это не должно быть DoStuff (e.nextElement()) внутри блока? – 2010-01-13 15:00:19

ответ

34

Enumeration не был изменен для поддержки Iterable, потому что это интерфейс не конкретный класс (например, Vector, который был модифицирован для поддержки интерфейса Collections).

Если Перечисление было изменено для поддержки Iterable, это сломало бы кучу кода людей.

+11

Тем не менее, учитывая, что для каждой поддержки для ** обоих ** Итерабельных ** и ** массивов, почему Солнце не включило Enumerable? – akuhn 2008-11-26 16:13:59

+8

@Adrian Kuhn: они не включали для каждой поддержки Iterator, а Enumerable ведет себя как Iterator, а не Iterable. – 2009-08-06 16:43:17

6

AFAIK Перечень является kinda "deprecated":

Итератора занимает место Перечисления в коллекции Java рамочного

Я надеюсь, что они будут менять Servlet API с JSR 315, чтобы использовать итератор вместо Перечисления.

44

Это не имеет значения для Enumeration для реализации Iterable. Iterable является заводским методом для Iterator. Enumeration аналогичен Iterator и поддерживает только состояние для одного перечисления.

Итак, будьте осторожны, пытаясь обернуть Enumeration как Iterable. Если кто-то передаст мне Iterable, я буду считать, что я могу называть его iterator(), создавая столько экземпляров Iterator, сколько захочу, и итерацию самостоятельно по каждому. Обернутый Enumeration не выполнит этот договор; не позволяйте вашему обернутому Enumeration избежать вашего собственного кода. (Кстати, я заметил, что Java 7-х DirectoryStream нарушает ожидания именно таким образом, и не должно быть позволено «бежать» тоже.)

Enumeration подобен Iterator, а не как Iterable. A Collection - Iterable. Iterator нет.

Вы не можете сделать это:

Vector<X> list = … 
Iterator<X> i = list.iterator(); 
for (X x : i) { 
    x.doStuff(); 
} 

Так что не имеет смысла делать это:

Vector<X> list = … 
Enumeration<X> i = list.enumeration(); 
for (X x : i) { 
    x.doStuff(); 
} 

Там нет Enumerable эквивалентно Iterable. Его можно было бы добавить, не нарушая ничего для работы в цикле, но в чем смысл? Если вы можете реализовать этот новый интерфейс Enumerable, почему бы просто не реализовать вместо этого Iterable?

72

Как простой и чистый способ использования перечисления с расширенным циклом, преобразовать в ArrayList с помощью java.util.Collections.list.

for (TableColumn col : Collections.list(columnModel.getColumns()) { 

(javax.swing.table.TableColumnModel.getColumns возвращает перечисление.)

Примечание, это может быть очень немного менее эффективной.

1

Если вы просто хотите, чтобы это было синтаксически немного чище, вы можете использовать:

while(e.hasMoreElements()) { 
    doStuff(e.nextElement()); 
} 
Смежные вопросы