当前位置: 首页 > 知识库问答 >
问题:

Java-在流上迭代的最干净的方法,保持索引的跟踪[重复]

曹鹏海
2023-03-14

我正试图找到一种干净的方法来复制ArrayList中的所有元素,但是要基于它的索引。

在JavaScript中,我们可以根据值进行过滤,但也可以根据索引进行过滤。所以我想要达到的目标是这样的:

// nums is []
for(let i = 0; i <nums.length; i++ {
   let copyNums = nums.filter((n, index) => index !== i);
}

到目前为止,我能做Java最好的就是这个,它又长又冗长。更不用说我不能使用i本身,因为它还不是最终版本,否则我会得到

lambda表达式中使用的变量应该是final或final

       // nums is ArrayList
       for (int i = 0; i < nums.size(); i++) {
            final int index = i;
            List<Integer> allElementsWithoutCurr = IntStream.range(0, nums.size())
                    .filter(j -> j != index)
                    .mapToObj(j -> nums.get(j))
                    .collect(Collectors.toList());
        }

当然有更好的方法在Java中实现这一点吗?

共有2个答案

寇丰
2023-03-14

你可以这样做,但这很难看。

List<Integer> list = List.of(1, 2, 3, 4, 5, 6, 7, 8, 9 );

int skip = 3;
List<Integer> result = new ArrayList<>(list.subList(0,skip));
result.addAll(list.subList(skip+1, list.size()));

System.out.println(result);

印刷品

[1, 2, 3, 5, 6, 7, 8, 9]

你也可以使用这个系统。arrayCopy以指定范围。但你仍然需要复制多份。如果你有一个大数组,复制它然后删除值可能效率不高(例如,ArrayLists是随机访问,值不容易删除。LinkedList值可以很容易地删除,但你必须先统计或返回它们。)因此,无论你怎么做,部分复制(imo)都将是一条出路。你目前做这件事的方式没有问题。

孔逸春
2023-03-14
List<Foo> result = new ArrayList<>(list);
result.remove(i);

对于长列表和低值的i,这可能有点慢,因为它必须将尾部元素向左移动,但是为了简洁和清晰,你无法打败它。

您可以使用流并通过使用AtomicInteger跟踪索引,其引用实际上是最终的,但其值可能会更改:

AtomicInteger index = new AtomicInteger();
List<Foo> result = list.stream()
  .filter(x -> index.getAndIncrement() != i)
  .collect(toList());

对于大型列表,这可能会更快,因为不需要左移,您可以在一个操作中完成流中的其他工作。

当然,如果你想根据索引过滤很多元素,你可以在不影响性能的情况下进行过滤。

对于流,如果只想直接处理结果,甚至可能不需要列表:

list.stream()
  .filter(x -> index.getAndIncrement() != i)
  .forEach(foo -> {doSomething with foo});
 类似资料:
  • 问题内容: 从Python 2.6的迭代器中获取最后一项的最佳方法是什么?例如说 从中获取最短代码/最干净的方法是什么? 我可以这样做,但是效率似乎不高: 问题答案:

  • 问题内容: 那就是我的做法: 有什么好处吗?如何避免那些意粉般的代码? 问题答案: 检出异步库,它用于控制流(异步内容),并且它有很多用于数组内容的方法:每种方法,过滤器,映射。查看github上的文档。这可能是您需要的: 每个(arr,迭代器,回调) 将迭代器函数并行应用于数组中的每个项目。调用迭代器时,将使用列表中的项目以及完成时的回调。如果迭代器将错误传递给此回调,则该函数的主回调将立即被错

  • 本文向大家介绍Java 8中迭代带有索引的流(Stream),包括了Java 8中迭代带有索引的流(Stream)的使用技巧和注意事项,需要的朋友参考一下 要在Java 8中迭代带有索引的流,代码如下- 示例 输出结果 名为Demo的类包含主要功能。 在此主要函数中,声明了一个字符串类型的数组,并使用AtomicInteger类创建了AtomicInteger实例。  “ getAndIncrem

  • 假设您希望对迭代器的元素进行流式处理;让我们使用一个的具体示例,它实现了。 给定,比方说: 在给定的情况下,JDK中是否有一个工厂方法返回?

  • 问题内容: 我已经开始使用gwt进行一些基本的Java编码,而我有点担心主类的繁重。 例如- 如何分隔密钥处理程序,因为它们触发了UI的许多更改,我如何才能将其移到单独的.class文件中,并且仍然能够访问主类中的所有各种小部件,而不必将所有内容传递给处理程序(即,我在click事件之后处理的所有小部件)。 我已经在Google上搜索过,但是没有遇到任何特别好的例子- 知道我可以阅读的任何易读的代

  • 问题内容: 我创建一个从如下: 我想保持与中相同的迭代顺序。如何使用该方法创建一个? 问题答案: 在2个参数的版本采用的是: 要使用4参数版本,您可以替换: 与: 为了使它更简洁,请编写一个新方法并使用该方法: