将列表划分为 n 大小的列表的有效方法
我有一个 ArrayList,我想将其分成 n 大小的较小的 List 对象,并对每个对象执行操作。 我当前的方法是使用 Java 中的 ArrayList 对象实现的。任何伪代码都可以。
for (int i = 1; i <= Math.floor((A.size() / n)); i++) {
ArrayList temp = subArray(A, ((i * n) - n),
(i * n) - 1);
// do stuff with temp
}
private ArrayList<Comparable> subArray(ArrayList A, int start,
int end) {
ArrayList toReturn = new ArrayList();
for (int i = start; i <= end; i++) {
toReturn.add(A.get(i));
}
return toReturn;
}
其中 A
是列表,n
是所需列表的大小
我认为在处理大小高达 100 万的相当大的列表时,这种方式会花费太多时间,所以我试图弄清楚什么会更有效率。
I have an ArrayList
, which I want to divide into smaller List
objects of n
size, and perform an operation on each.
My current method of doing this is implemented with ArrayList
objects in Java. Any pseudocode will do.
for (int i = 1; i <= Math.floor((A.size() / n)); i++) {
ArrayList temp = subArray(A, ((i * n) - n),
(i * n) - 1);
// do stuff with temp
}
private ArrayList<Comparable> subArray(ArrayList A, int start,
int end) {
ArrayList toReturn = new ArrayList();
for (int i = start; i <= end; i++) {
toReturn.add(A.get(i));
}
return toReturn;
}
where A
is the list and n
is the size of the desired lists
I believe this way is taking too much time when working with considerably large lists of up to 1 million in size, so I'm trying to figure out what would be more efficient.
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(18)
您需要做一些利用 List.subList(int, int) 视图而不是复制每个子列表。要真正轻松地做到这一点,请使用 Guava 的 Lists.partition(List, int) 方法:
请注意,这和许多对于不是
RandomAccess
的List
(例如LinkedList
),效率不高。You'll want to do something that makes use of List.subList(int, int) views rather than copying each sublist. To do this really easily, use Guava's Lists.partition(List, int) method:
Note that this, like many things, isn't very efficient with a
List
that isn'tRandomAccess
(such as aLinkedList
).例如:
For example:
如果您正在使用列表,我使用“Apache Commons Collections 4”库。它在 ListUtils 类中有一个分区方法:
该方法改编自 http://code.google .com/p/guava-libraries/
If you are working with a list I use the "Apache Commons Collections 4" library. It has a partition method in the ListUtils class:
This method is adapted from http://code.google.com/p/guava-libraries/
如果您不想使用库,这是我的解决方案
1. 划分为 N 个相等的部分:
2. 划分为 N 个项目的集合:
此处的操作:
https://ideone.com/QiQnbE
If you don't want to use a library, here's my solution
1.To partition in N equal parts:
2. To partition in sets of N items:
In action here:
https://ideone.com/QiQnbE
// 测试数据
// 使用 java 8 流和 list.subList 的一行(语句)
// Testing data
// One line(statement) with java 8 stream and list.subList
好吧,在看到 ColinD 的答案(+1)之前我自己写了一个,使用 Guava 绝对是可行的方法。留下来太有趣了,所以下面给你的是列表的副本而不是视图,所以 GUava 肯定比这更有效率。我发布此内容是因为写起来很有趣,而不是暗示它同样有效:
Hamcrest 测试(无论如何之一):
代码:
Well i wrote one myself before i saw ColinD's answer (+1) and using Guava is definitely the way to go. It was too much fun to leave alone and so the below gives you a copy of the list rather than views so GUava's is definitely more efficient than this. I'm posting this because it was fun to write rather than suggesting it is as efficient:
The Hamcrest test (one of anyway):
The code:
我刚刚实现了列表分区,因为我无法使用库。
所以我想在这里分享我的代码:
以及基于testng的单元测试。
I just implemented a list partitioning, because I couldn't use a library.
So I want to share my code here:
And the unit test based on testng.
使用 Java 8 一行:
One line using Java 8:
由于您想优化性能,因此应该使用并行流而不是 for 循环。这样就可以使用多线程。
您还可以使用其他方式来处理流,例如收集或映射(如果符合您的目的)。
Since you want to optimise your performance you should use a parallel stream instead of a for loop. This way you can use multiple threads.
You can also use other ways to work with the stream for example collect or map if it matches your purpose.
如果我被迫在不依赖任何第三方库的情况下执行此操作,我会选择类似
Complete example:
的结果
Had I compelled to do this without relying on any 3rd party library, I'd go with something like
Complete example:
resulting in
如果您正在处理数组,则可以使用 System.arraycopy() 。
If you are dealing with arrays, you can use System.arraycopy() for that.
这是一种将 List 划分为子列表数组的方法,它确保除最后一个子列表之外的所有子列表都具有相同数量的元素:
如果您想保证 numPartitions 数组大小,那么您需要:
Here is a way to partition a List into an array of sublists, which ensures all but the last sublist have equal number of elements:
If you want to guarantee
numPartitions
array size then you want:输出:
Output:
基于@BrownRecluse[response][1],你可以实现这个方法:
这是一个例子:
Based on @BrownRecluse[ response][1], you can implement this method:
And this is a example:
JEP 461:Stream Gatherers Java 22 预览语言功能添加了对将流分区为列表的内置支持给定的大小。这可用于对
List
的元素进行分区,然后对每个分区执行操作。这使用新的
Stream.gather
方法,带有新的内置Gatherers.windowFixed
收集器,用于将List
中元素的Stream
转换为流<列表>
。Javadocs
<代码>收集器:
Stream.gather
:Gatherers.windowFixed
The JEP 461: Stream Gatherers Java 22 preview language feature adds built-in support for partitioning a stream into lists of a given size. This can be used to partition the elements of your
List
and then perform your operation on each partition.This uses the new
Stream.gather
method with the new built-inGatherers.windowFixed
gatherer to convert theStream<T>
of elements from theList
to aStream<List<T>>
.Javadocs
Gatherer
:Stream.gather
:Gatherers.windowFixed
又怎样呢
?
What about
?