15

ArrayList特定の基準を満たしている場合、Javaから要素を削除したいと思います。

すなわち:

for (Pulse p : pulseArray) {
    if (p.getCurrent() == null) {
        pulseArray.remove(p);
    }
}

これが機能しない理由は理解できますが、これを行う良い方法は何ですか?

4

9 に答える 9

24

を使用しIteratorて反復しremove、イテレータの関数 (リストの関数ではない) を使用する必要があります。

Iterator<Pulse> iter = pulseArray.iterator();
while (iter.hasNext()) {
  Pulse p = iter.next();
  if (p.getCurrent()==null) iter.remove();
}

Iterator#remove関数はオプションであると言われていますが、ArrayList の反復子によって実装されていることに注意してください。

ArrayList.java からのこの具象関数のコードは次のとおりです。

765         public void remove() {
766             if (lastRet < 0)
767                 throw new IllegalStateException();
768             checkForComodification();
769 
770             try {
771                 ArrayList.this.remove(lastRet);
772                 cursor = lastRet;
773                 lastRet = -1;
774                 expectedModCount = modCount;
775             } catch (IndexOutOfBoundsException ex) {
776                 throw new ConcurrentModificationException();
777             }
778         }
779 
780         final void checkForComodification() {
781             if (modCount != expectedModCount)
782                 throw new ConcurrentModificationException();
783         }
784     }

このexpectedModCount = modCount;行は、反復中に使用すると例外がスローされない理由です。

于 2012-11-09T21:57:49.420 に答える
4

イテレータを使用する必要はありません。Java 8 (ストリーミングおよびフィルタリング機能とラムダ) を使用すると、1 行で実現できます。たとえば。指定した操作を実行するために必要なコードは次のとおりです。

pulseArray = pulseArray.stream().filter(pulse -> pulse != null).collect(Collectors.toList());
于 2015-10-10T14:32:56.777 に答える
2

同じリストから要素を削除すると、インデックスが乱れます。以下のように少し違った方法で試してください。

  for (int i=0; i < pulseArray.size(); i++) {
     Pulse p = (Pulse)pulseArray.get(i);
     if (p.getCurrent() == null) {
        pulseArray.remove(p);
        i--;//decrease the counter by one
     }
  }
于 2012-11-09T22:02:17.950 に答える
2

イテレータを使用する代わりに、Guavaコレクション ライブラリを使用できます。これには、より機能的であるという利点があります(そのようなことに興味がある場合):

Predicate<Pulse> hasCurrent = new Predicate<Pulse>() {
  @Override public boolean apply(Pulse input) {
    return (input.getCurrent() != null);
  }
};

pulseArray = Lists.newArrayList(Collections2.filter(pulseArray, hasCurrent));
于 2012-11-09T23:11:14.770 に答える
0

コレクションのメソッドを使用して反復しているコレクションを変更することはできません。ただし、一部の反復子 ( ArrayLists の反復子を含む) は、反復する順序でメソッドを削除できるメソッドをサポートしremove()ています。

Iterator<Pulse> iterator = pulseArray.iterator();
while (iterator.hasNext()) {
  Pulse p = iterator.next();
  if (p.getCurrent() == null) {
    iterator.remove();
  }
}
于 2012-11-09T21:59:41.547 に答える
-2

Iterator を使用すると、arraylist を反復処理しながらリストを変更することができます。

于 2012-11-09T22:39:55.123 に答える