在我的项目中,用户输入随机字母。然后我遍历my_list
以查看my_list
中是否出现任何随机字母。如果是这样,我会将其从my_list
删除。
示例:
List<String> my_list
包含:[a, b, c, d]
List<String> rand
包含:[r, a]
目标:a
将从my_list
问题:Iterator
循环my_list
搜索字母r
。字母r
不在my_list
中。但是a
退出循环并且iterator
仍然保留在a
my_list
。
有人可以告诉我为什么我的循环在第一个字母后会一直断开吗?
这是我的代码:
public void removeLetters( List<String> my_list, List<String> rand ) {
Iterator<String> i = my_list.iterator();
for( String s : rand ) {
while( i.hasNext() ) {
Object o = i.next();
if( o.toString().equals( s ) ) {
i.remove();
i = my_list.iterator();
break;
}
}
}
}
我希望我能很好地解释我的问题。如果我需要详细解释,请告诉我。
由于
答案 0 :(得分:4)
尝试在for循环中创建Iterator
。
for(String s : rand) {
Iterator<String> i = my_list.iterator();
while(i.hasNext()) {
...
}
}
答案 1 :(得分:2)
问题是在你的内部循环中,你通过外部循环的第一次迭代到达迭代器的末尾。然后当for的第二次迭代开始时,迭代器i hasNext方法总是返回false,似乎什么也没做,就像你说的那样。
你应该为你的每个新的
重新初始化你的迭代器答案 2 :(得分:0)
i.remove();
这是你的问题。您必须按照说明将其从my_list中删除。
所以使用
my_list.remove();
答案 3 :(得分:0)
或者,只需使用一个班轮:
my_list.removeAll(rand);
您还可以使用List的功能来平等删除对象:
for(String s: rand) {
my_list.remove(s);
}
如果你想迭代,这正是java.util.AbstractCollection的作用:
Iterator<String> it = my_list.iterator();
while (it.hasNext()) {
if (rand.contains(it.next())) {
it.remove();
}
}
答案 4 :(得分:0)
您需要将Iterator重置为其开头,然后循环查看下一个项目。
答案 5 :(得分:0)
您只能通过Iterator一次。考虑一下:一旦i.hasNext()
返回false
,您就会退出内循环,绕过外循环,然后再次调用i.hasNext()
。为什么现在开始返回true
?
结论:每次重启外循环时都必须创建一个新的迭代器(基本上在循环内移动my_list.iterator()
调用)
更好的是,迭代列表一次,并在输入列表上使用contains()
:
for(Iterator it = my_list.iterator(); it.hasNext(); ) {
if(rand.contains(it.Next()) {
it.remove();
}
}
如果输入列表(rand)可能足够大以至于重要,您可能希望在循环之前将其转换为Set:rand = new HashSet(rand);
这将使算法成为线性而非二次的。
答案 6 :(得分:0)
是否有理由不使用contains?
public void removeLetters(List<String> my_list, List<String> rand)
{
List<String> updatedList = new ArrayList<String>();
for (String s : my_list)
{
if (!rand.contains(s))
{
updatedList.add(s);
}
}
}