Java 流生成直到限制,但仅匹配谓词
如何使用100个元素的流生成列表。但是列表中的所有元素都应该匹配一个谓词 测试代码:Java 流生成直到限制,但仅匹配谓词,java,java-stream,Java,Java Stream,如何使用100个元素的流生成列表。但是列表中的所有元素都应该匹配一个谓词 测试代码: import java.util.ArrayList; import java.util.List; import java.util.Random; import java.util.function.Predicate; import java.util.stream.Stream; public class Main { // My predicate public static
import java.util.ArrayList;
import java.util.List;
import java.util.Random;
import java.util.function.Predicate;
import java.util.stream.Stream;
public class Main {
// My predicate
public static Predicate<Integer> isBig() {
return p -> p > 10;
}
public static void main(String args[]) {
List<Integer> list = new ArrayList<>();
Stream.generate(new Random()::nextInt)
.limit(100)
//???????
.forEach(a -> list.add(a));
// Always needs to be 100
System.out.println(list.size());
}
}
如何做到这一点?像这样:
List<Integer> list = Stream.generate(new Random()::nextInt)
.filter(p -> p > 10)
.limit(100).collect(Collectors.toList());
或者像这样:
public class Main {
private static boolean isBig(Integer input) {
return input > 10;
}
public static void main(String args[]) {
List<Integer> list = Stream.generate(new Random()::nextInt)
.filter(Main::isBig)
.limit(100).collect(Collectors.toList());
}
}
编辑:
如果您可以做任何您想做的事情,请不要对具有伪随机数源的流使用filter方法
如果你这样做了,你将在最好的情况下运行性能下降,在最坏的情况下进入挂起程序
这是因为如果你只是随机数和过滤他们,你很可能会产生更多的数字比你需要的。
例如,如果您想要100个偶数随机数,您平均需要生成200个随机数
最坏的情况是,如果PRNG有一个坏种子,并且只通过与谓词不匹配的数字循环,因此您永远无法收集所需数量的数字
总结:如果你需要n个满足某个谓词的随机数,例如正数,如果可能,只需创建n个随机数,并将与谓词不匹配的随机数映射到匹配的随机数,例如,将负数的绝对值设为只有正数
原始答案
如果要过滤流,只需使用方法过滤器:
像
随机r=新随机;
列表=Stream.generate->r.nextInt
.filtern->n>0//过滤正数
.filtern->n%2==0//对偶数进行筛选
有限公司
.toList;
但是你应该小心你的流源。如果使用PRNG,则应尽量限制生成的数字范围
例如,上面的例子可以通过
Random r = new Random();
List<Integer> list = Stream.generate(() -> r.nextInt(Integer.MAX_VALUE/2) * 2)
.limit(10)
.collect(Collectors.toList());
并且是首选,因为第一个示例可能会遇到一个伪随机数循环,而这些伪随机数永远不会满足要求
所以一般来说。如果您处理的是随机源,请尝试从输入中创建所需的数字,而不要过滤随机输入。将过滤器置于限制之前。您对流中元素的具体偏好是什么?您试图根据什么进行筛选?stream.filterpredicate::test.limit100.collectCollectors.toList;或者类似的。仅显示@Slaw引用的代码示例。@BeUndead使用筛选器不会使列表大小始终为100。正确。不过,使用我也包含的“限制”也可以。我使用了您的代码,但使用筛选器时列表的大小不是100。大小必须始终为100。所以它需要不断填充匹配的整数,直到它达到100。这是因为我使用10作为限制值,就像一个例子。只需将极限方法的参数更改为你想要的任何一个。@奥尼尔也请阅读整个答案。我非常不喜欢使用随机数源结合后面的随机数过滤。@ O-NIEL,您也可以考虑使用,虽然该方法返回一个ItSt流而不是流。我使用了您的代码,但是使用过滤器时列表的大小不是100。大小必须始终为100。所以它需要不断填充匹配的整数,直到它达到100。我刚刚运行了它,它正好是100。我的错,我在过滤器之前设置了限制。
Random r = new Random();
List<Integer> list = Stream.generate(() -> r.nextInt(Integer.MAX_VALUE/2) * 2)
.limit(10)
.collect(Collectors.toList());