4

我正在尝试搜索数组列表以查找一个值(可能会再次出现)并删除该值的所有实例。我还想从单独的数组列表中删除位于同一位置的值。两个 ArrayList 都是ArrayList<String>.

例如,我正在寻找 ArrayList2 中的数字 5:

ArrayList 1       ArrayList2
cat               1
pig               2
dog               5
chicken           3
wolf              5

在这两个位置找到数字 5 后,我想从 ArrayList1 中删除 dog 和 wolf。我的代码没有错误,但它似乎并没有真正删除我的要求。

//searching for
String s="5";
//for the size of the arraylist
for(int p=0; p<ArrayList2.size(); p++){
 //if the arraylist has th value of s
 if(ArrayList2.get(p).contains(s)){
   //get the one to remove
   String removethis=ArrayList2.get(p);
   String removetoo=ArrayList1.get(p);
   //remove them
   ArrayList2.remove(removethis);
   ArrayList1.remove(removetoo);
  }
}

当我打印 arrayLists 时,它们看起来基本没有变化。有人看到我做错了吗?

4

8 回答 8

11

当您同时从数组中循环和删除项目时,您编写的算法是不正确的,因为它会在每次删除后跳过下一个项目(由于您递增 p 的方式)。考虑这个替代方案:

int s = 5;
int idx = 0;

while (idx < ArrayList2.size())
{
   if(ArrayList2.get(idx) == s)
   {
     // Remove item
     ArrayList1.remove(idx);
     ArrayList2.remove(idx);
  }
  else
  {
    ++idx;
  }
}
于 2012-08-24T14:27:46.613 回答
3

如果要遍历集合并删除同一集合的元素,则必须使用Iterator,例如:

List<String> names = ....
List<Integer> numbers = ....
int index = 0;
Iterator<String> i = names.iterator();
while (i.hasNext()) {
   String s = i.next(); // must be called before you can call i.remove()
   if (s.equals("dog"){
       i.remove();
       numbers.remove(index);
   }
   index++;
}

编辑

在您的情况下,您必须手动增加一个变量才能从另一个列表中删除项目。

于 2012-08-24T14:24:43.863 回答
1

您可以使用两个迭代器:

Iterator<String> i1 = arrayList1.iterator();
Iterator<Integer> i2 = arrayList2.iterator();
while (i1.hasNext() && i2.hasNext()) {
  i1.next();
  if (i2.next() == s) {
    i1.remove();
    i2.remove();
  }
}

尽管正如已经指出的那样,使用地图可能会更容易。

于 2012-08-24T14:31:48.553 回答
0

我认为 contains 方法比较了两个对象。但是,对象“s”与 ArrayList 中的对象不同。您应该使用类型化数组(即 ArrayList)并确保比较每个对象的值,而不是对象本身...

于 2012-08-24T14:26:40.653 回答
0

您应该如下声明您的清单 -

List<String> list1 = new ArrayList<String>();
//...
List<Integer> list2 = new ArrayList<Integer>();
//...

而不是contains方法使用equals方法。

还可以在迭代列表时删除Iterator,您可以获得如下 -

Iterator<String> it1 = list1.iterator();
Iterator<Integer> it2 = list2.iterator();

//...
于 2012-08-24T14:27:39.093 回答
0

您可能想检查 ArrayList 的indexOf()方法,但在迭代列表元素时从列表中删除时必须小心。

于 2012-08-24T14:30:16.160 回答
0

这是一个直接的解决方案:

List<Integer> origNums = new ArrayList<Integer>(nums);
Iterator<String> animalIter = animals.iterator();
Iterator<Integer> numIter = nums.iterator();

while (animalIter.hasNext()) {
    animalIter.next();

    // Represents a duplicate?
    if (Collections.frequency(origNums, numIter.next()) > 1) {

        // Remove current element from both lists.
        animalIter.remove();
        numIter.remove();
    }
}

System.out.println(animals); // [cat, pig, chicken]
System.out.println(nums);    // [1, 2, 3]
于 2012-08-24T14:32:28.733 回答
0

我同意 Makoto 的观点,使用 Map 可能更有益。如果您将仅使用 ArrayList2 的值进行搜索,则一个键有多个值。例如,5 指的是狗和狼。为此,您可以将值列表添加到键 - 5。

HashMap aMap = HashMap();

ArrayList key5 = new ArrayList();

key5.add("dog");
key5.add("wolf");

aMap.put(5, key5);

因此,当您需要删除 5 的所有值时,您可以

aMap.remove(5);

它将删除包含 dog 和 wolf 的列表。

于 2012-08-24T14:49:09.363 回答