如果符合某个条件,我想从Java中的ArrayList
中删除一个元素。
即:
for (Pulse p : pulseArray) {
if (p.getCurrent() == null) {
pulseArray.remove(p);
}
}
我能理解为什么这不起作用,但是这样做的好方法是什么?
答案 0 :(得分:16)
您必须使用Iterator
迭代迭代器的remove
函数(不是列表):
Iterator<Pulse> iter = pulseArray.iterator();
while (iter.hasNext()) {
Pulse p = iter.next();
if (p.getCurrent()==null) iter.remove();
}
请注意,Iterator#remove函数被称为optionnal,但是由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;
行是在迭代时使用它时不会抛出异常的原因。
答案 1 :(得分:13)
您可以使用Collection::removeIf(Predicate filter),这是一个简单的示例:
final Collection<Integer> list = new ArrayList<>(Arrays.asList(1, 2));
list.removeIf(value -> value < 2);
System.out.println(list); // outputs "[2]"
答案 2 :(得分:3)
无需使用迭代器。使用 Java 8 (流式传输和过滤功能以及lambdas),您可以使用一行完成它。 例如。执行指定操作所需的代码为:
pulseArray = pulseArray.stream().filter(pulse -> pulse != null).collect(Collectors.toList());
答案 3 :(得分:2)
作为使用迭代器的替代方法,您可以使用Guava集合库。这样做的好处是更多functional(如果您涉及到这类事情):
Predicate<Pulse> hasCurrent = new Predicate<Pulse>() {
@Override public boolean apply(Pulse input) {
return (input.getCurrent() != null);
}
};
pulseArray = Lists.newArrayList(Collections2.filter(pulseArray, hasCurrent));
答案 4 :(得分:1)
您可以实现接口 Predicate 覆盖抽象方法 boolean test(T);
使用 removeIf(Predicate p) 方法从您的 列表。
例如:
List<Book> bookList = new ArrayList<>();
bookList.add(new Book(101, "bookname1"));
bookList.add(new Book(102, "booknamelong2"));
bookList.removeIf(new LongBookNames())
public class LongBookNames implements Predicate<Book> {
@Override
public boolean test(Book book) {
return book.getBookName.length() >10;
}
}
答案 5 :(得分:0)
您无法使用集合上的方法更改正在迭代的集合。但是,一些迭代器(包括ArrayList
上的迭代器)支持remove()
方法,该方法允许您按照迭代的顺序删除方法。
Iterator<Pulse> iterator = pulseArray.iterator();
while (iterator.hasNext()) {
Pulse p = iterator.next();
if (p.getCurrent() == null) {
iterator.remove();
}
}
答案 6 :(得分:0)
如果从相同列表中删除元素,则索引会受到干扰。尝试与以下几点不同:
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
}
}
答案 7 :(得分:0)
当单个 ArrayList 有多个类型的对象并且一个对象的计数 == 0 时使用下面一个,然后将其从 pulseArray
<块引用>常量.java
public class ViewType {
public static final int PULSE = 101;
public static final int HEARTBEAT = 102;
}
<块引用>
BaseModel.java(这是基础模型)
public interface BaseModel {
int getViewType();
}
<块引用>
PulseModel.java(使用 BaseModel 实现)
public class PulseModel implements BaseModel {
@Override
public int getViewType() {
return Constants.ViewType.PULSE;
}
@SerializedName("PulseId")
@Expose
private String pulseId;
@SerializedName("Count")
@Expose
private String count;
}
<块引用>
从 pulseArray 中移除 PulseModel 对象,其中 Count = 0
pulseArray.removeIf(
(BaseModel model) -> {
boolean remove = false;
if (model instanceof PulseModel) {
remove = (((PulseModel) model).getCount() == 0);
if (remove) {
//Success
}
}
return remove;
});
答案 8 :(得分:-1)
使用迭代器可以让你在迭代arraylist时修改列表