我想知道为什么Iterable
界面不提供stream()
和parallelStream()
方法.考虑以下课程:
public class Hand implements Iterable<Card> {
private final List<Card> list = new ArrayList<>();
private final int capacity;
//...
@Override
public Iterator<Card> iterator() {
return list.iterator();
}
}
Run Code Online (Sandbox Code Playgroud)
这是一个Hand的实现,因为你可以在玩卡片游戏时手中拿着牌.
基本上它包装a List<Card>
,确保最大容量并提供一些其他有用的功能.最好直接实现它作为一个List<Card>
.
现在,为了方便起见,我认为实现它会很好Iterable<Card>
,这样如果你想循环它就可以使用增强的for循环.(我的Hand
班级也提供了一种get(int index)
方法,因此Iterable<Card>
在我看来是合理的.)
该Iterable
接口提供以下内容(省略javadoc):
public interface Iterable<T> {
Iterator<T> iterator();
default void forEach(Consumer<? super T> action) {
Objects.requireNonNull(action);
for (T t : this) {
action.accept(t);
}
}
default Spliterator<T> …
Run Code Online (Sandbox Code Playgroud) 我有一个第三方图书馆给了我一个Enumeration<String>
.我想懒洋洋地与枚举工作作为Java 8 Stream
,呼叫之类的东西filter
,map
并flatMap
在其上.
是否有现有的库?我已经引用了Guava和Apache Commons,所以如果其中任何一个都有理想的解决方案.
或者,是什么把一个最好/最简单的方式Enumeration
进入Stream
,同时保留所有的懒惰天性?
我有几张包含大量数据的表(大约1亿条记录).所以我不能将这些数据存储在内存中,但是我希望使用类来传输这个结果集java.util.stream
并将此流传递给另一个类.我读了关于Stream.of
和Stream.Builder
运算符,但它们是内存中的缓冲流.那么有什么方法可以解决这个问题吗?提前致谢.
更新#1
好吧,我用Google搜索并找到了jooq库.我不确定,但看起来它可能适用于我的测试用例.总而言之,我有几张包含大量数据的表格.我想流式传输我的结果集并将此流传输到另一个方法.像这样的东西:
// why return Stream<String>? Because my result set has String type
private Stream<Record> writeTableToStream(DataSource dataSource, String table) {
Stream<Record> record = null;
try (Connection connection = dataSource.getConnection()) {
String sql = "select * from " + table;
try (PreparedStatement pSt = connection.prepareStatement(sql)) {
connection.setAutoCommit(false);
pSt.setFetchSize(5000);
ResultSet resultSet = pSt.executeQuery();
//
record = DSL.using(connection)
.fetch(resultSet).stream();
}
} catch (SQLException sqlEx) {
logger.error(sqlEx);
}
return record;
}
Run Code Online (Sandbox Code Playgroud)
可以请有人建议,我是否正确?谢谢.
更新#2
我在 …
在Java中,可以轻松地生成无限流Stream.generate(supplier)
.但是,我需要生成一个最终完成的流.
想象一下,例如,我想要一个目录中所有文件的流.文件数量可能很大,因此我无法预先收集所有数据并从中创建流(via collection.stream()
).我需要逐个生成序列.但是流很明显会在某个时刻完成,终端运营商喜欢(collect()
或findAny()
)需要对它进行处理,因此Stream.generate(supplier)
不适合这里.
有没有合理的简单方法在Java中执行此操作,而不是自己实现整个Stream接口?
我可以想到一个简单的黑客 - 用无限做它Stream.generate(supplier)
,并在获取所有实际值时提供null或抛出异常.但是它会破坏标准的流操作符,我只能将它用于我自己的操作符,这些操作符都知道这种行为.
澄清
评论中的人提议我takeWhile()
操作员.这不是我的意思.如何更好地表达问题...我不是在问如何过滤(或限制)现有的流,我问如何动态创建(生成)流,而不是先加载所有元素,但是流会有有限的大小(事先未知).
解
我正在寻找的代码是
Iterator it = myCustomIteratorThatGeneratesTheSequence();
StreamSupport.stream(Spliterators.spliteratorUnknownSize(it, Spliterator.DISTINCT), false);
Run Code Online (Sandbox Code Playgroud)
我刚看了一下java.nio.file.Files
,该list(path)
方法是如何实现的.
我想知道何时可以IntStream.range
有效使用.我有三个原因,我不确定它有多大用处IntStream.range
.
(请将开头和结尾视为整数.)
如果我想要一个数组,[start, start+1, ..., end-2, end-1]
下面的代码要快得多.
int[] arr = new int[end - start];
int index = 0;
for(int i = start; i < end; i++)
arr[index++] = i;
Run Code Online (Sandbox Code Playgroud)
这可能是因为toArray()
在IntStream.range(start, end).toArray()
非常缓慢.
我使用MersenneTwister来重排数组.(我在网上下载了MersenneTwister课程.)我认为没有办法IntStream
使用MersenneTwister 进行随机播放.
我不认为刚开int
从数字start
到end-1
是很有用的.我可以使用for(int i = start; i < end; i++)
,这似乎更容易,而不是慢.
你能告诉我什么时候应该选择IntStream.range
吗?
我有一个涉及httprequest的错误,有时会发生这种错误,因此我想在发生这种情况时记录HttpGet和HttpPost请求的内容.
所以,让我们说,我创建像这样的HttpGet:
HttpGet g = new HttpGet();
g.setURI(new URI("http://www.google.com"));
g.setHeader("test", "hell yeah");
Run Code Online (Sandbox Code Playgroud)
这是我想要的字符串表示:
GET / HTTP/1.1
Host: www.google.com
test: hell yeah
Run Code Online (Sandbox Code Playgroud)
有了post请求,我还想获得内容字符串.
在java for android中最简单的方法是什么?
我有以下集合类型:
Map<String, Collection<String>> map;
Run Code Online (Sandbox Code Playgroud)
我想map.size()
从每个Key的集合中的单个值创建每个组的唯一组合.
例如,假设地图如下所示:
A, {a1, a2, a3, ..., an}
B, {b1, b2, b3, ..., bn}
C, {c1, c2, c3, ..., cn}
Run Code Online (Sandbox Code Playgroud)
我希望获得的List<Set<String>>
结果是一个结果,看起来类似于(排序并不重要,它只需要是一个由所有可能的组合组成的'完整'结果):
{a1, b1, c1},
{a1, b1, c2},
{a1, b1, c3},
{a1, b2, c1},
{a1, b2, c2},
{a1, b2, c3},
...
{a2, b1, c1},
{a2, b1, c2},
...
{a3, b1, c1},
{a3, b1, c2},
...
{an, bn, cn}
Run Code Online (Sandbox Code Playgroud)
这基本上是一个计数问题,但我想看看是否可以使用Java 8流解决方案.
Stream
继承一个iterator()方法来生成一个Iterator
.
例如,给定这个字符串:
String input = "this\n" +
"that\n" +
"the_other";
Run Code Online (Sandbox Code Playgroud)
...我需要将字符串的这些部分作为 anIterable
传递给特定的库。调用input.lines()
产生一个Stream
. 所以如果我能把它Stream
变成Iterable
它的一个元素,我会很高兴的。
看看下面的课程我做了:
public class FibonacciSupplier implements Iterator<Integer> {
private final IntPredicate hasNextPredicate;
private int beforePrevious = 0;
private int previous = 1;
private FibonacciSupplier(final IntPredicate hasNextPredicate) {
this.hasNextPredicate = hasNextPredicate;
}
@Override
public boolean hasNext() {
return hasNextPredicate.test(previous);
}
@Override
public Integer next() {
int result = beforePrevious + previous;
beforePrevious = previous;
previous = result;
return result;
}
public static FibonacciSupplier infinite() {
return new FibonacciSupplier(i -> true);
}
public static FibonacciSupplier finite(final IntPredicate predicate) {
return new FibonacciSupplier(predicate);
} …
Run Code Online (Sandbox Code Playgroud) 假设您想要流式迭代器的元素; 让我们使用一个具体的例子Scanner
来实现Iterator<String>
.
给出一个Iterator
,说:
// Scanner implements Iterator<String>
Iterator<String> scanner = new Scanner(System.in);
Run Code Online (Sandbox Code Playgroud)
从中创建的选项Stream<String>
很笨重:
StreamSupport.stream(
Spliterators.spliteratorUnknownSize(scanner, Spliterator.ORDERED), false);
Run Code Online (Sandbox Code Playgroud)
或稍微简洁,但迟钝:
StreamSupport.stream(
((Iterable<String>) () -> new Scanner(System.in)).spliterator(), false);
Run Code Online (Sandbox Code Playgroud)
在JDK中的某个地方是否有一个返回Stream<T>
给定的工厂方法Iterator<T>
?