Java Inner Class Iterator Problem
-
18-09-2019 - |
Question
I'm having difficulty using an inner Iterator
.
private List<List<? extends HasWord>> sentences = new ArrayList<List<? extends HasWord>>();
private Iterator<String> wordIterator = new Words();
private class Words implements Iterator<String> {
int currSentence = 0;
int currWord = 0;
@Override
public boolean hasNext() {
return currSentence != sentences.size() - 1 && currWord != sentences.get(currSentence).size() - 1;
}
@Override
public String next() {
String nextWord = sentences.get(currSentence).get(currWord).word();
currSentence++;
currWord++;
return nextWord;
}
@Override
public void remove() {
throw new UnsupportedOperationException();
}
}
Then, I try to iterate over it:
for (String s : wordIterator) { //Error: Can only iterate over an array or an instance of java.lang.Iterable
words.add(s);
But it doesn't work. (See commented compiler error on the problematic line). What am I doing wrong here?
On an engineering note, do is the right way to solve my problem? I have a bunch of loops of this form:
for (List<? extends HasWord> sent : sentences) {
for (HasWord token : sent) {
//do stuff
}
}
So I decided an Iterator
would be cleaner. Is this overkill, or is there another way you'd do it?
Solution
There's nothing fundamentally wrong with having two nested for
loops to do this, but I think this would be cleaner:
public class Words implements Iterator<String> {
private final Iterator<HasWord> sentences;
private Iterator<String> currentSentence;
public boolean hasNext() {
return currentSentence.hasNext() || sentences.hasNext();
}
public String next() {
if (currentSentence.hasNext()) {
return currentSentence.next();
}
currentSentence = sentences.next();
return next(); // will return the first word of the next sentence
}
//remove() omitted for brevity
}
Return a new instance of this class every time you need an iterator over several sentences, and initialize the sentences
field using sentences.iterator();
(Edited after reading your question more carefully)
OTHER TIPS
private class Words implements Iterator<String>, Iterable<String> {
...
public Iterator<String> iterator() {
return this;
}
...
}
Licensed under: CC-BY-SA with attribution
Not affiliated with StackOverflow