gpt4 book ai didi

rust - future.then() 如何返回一个 Future?

转载 作者:行者123 更新时间:2023-12-03 11:29:11 29 4
gpt4 key购买 nike

下面的函数,取自 here :

fn connection_for(
&self,
pool_key: PoolKey,
) -> impl Future<Output = Result<Pooled<PoolClient<B>>, ClientError<B>>> {

let checkout = self.pool.checkout(pool_key.clone());
let connect = self.connect_to(pool_key);

let executor = self.conn_builder.exec.clone();
// The order of the `select` is depended on below...
future::select(checkout, connect).then(move |either| match either {
...
应该返回 Future .但是,它返回的返回结果为
    future::select(checkout, connect).then(...)
哪里 .then做这个:
fn then<Fut, F>(self, f: F) -> Then<Self, Fut, F>
哪个不是 Future .这怎么可能?
我试图了解此函数返回的内容。这是'.then'的结尾:
       Either::Right((Err(err), checkout)) => Either::Right(Either::Right({
if err.is_canceled() {
Either::Left(checkout.map_err(ClientError::Normal))
} else {
Either::Right(future::err(ClientError::Normal(err)))
}
})),
看起来它返回 Either::Right(Either::Right东西。我糊涂了。

最佳答案

.then()用于将两个 future 链接在一起。它返回一个 Then<Fut1, Fut2, F> ,这是一个 Future这样做的工作是:轮询第一个 future ,使用给定函数处理结果,并轮询产生的 future 。

Either 类型旨在将具有相同关联输出的两个不同 future 组合成一个类型。假设您正在创建一个函数,该函数将根据输入返回两个不同的 future :

async fn do_a() -> () {}
async fn do_b() -> () {}

fn do_something(cond: bool) -> impl Future<Output = ()> {
if cond {
do_a()
}
else {
do_b()
}
}
This won't compile因为 Future s 由 do_a() 返回和 do_b()是不同的类型。 Rust 编译器非常友好地建议使用 Box<dyn Future>动态返回不同的类型,但是有时出于性能原因不需要额外的间接访问,也没有必要。
以上可以实现返回一个具体的 Future使用 Either .
use std::future::Future;
use futures::future::Either;

async fn do_a() -> () {}
async fn do_b() -> () {}

fn do_something(cond: bool) -> impl Future<Output = ()> {
if cond {
Either::Left(do_a())
}
else {
Either::Right(do_b())
}
}
有问题的链接代码看起来有点粗糙,因为它不仅要协调两个不同的 future ,而且要协调五个。但是你可以嵌套 Either s 没有问题,因为它们本身是 Future s。它更像这样:
use std::future::Future;
use futures::future::Either;

async fn do_a() -> () {}
async fn do_b() -> () {}
async fn do_c() -> () {}
async fn do_d() -> () {}
async fn do_e() -> () {}

fn do_something(cond1: bool, cond2: bool, cond3: bool) -> impl Future<Output = ()> {
if cond1 {
Either::Left(do_a())
}
else if cond2 {
if cond3 {
Either::Right(Either::Left(Either::Left(do_b())))
}
else {
Either::Right(Either::Left(Either::Right(do_c())))
}
}
else {
if cond3 {
Either::Right(Either::Right(Either::Left(do_d())))
}
else {
Either::Right(Either::Right(Either::Right(do_e())))
}
}
}
这一切最终都会创建一个 impl Future<Output = Result<Pooled<PoolClient<B>>, ClientError<B>>>因为所有单个 future 它可能会产生每个返回 Result<Pooled<PoolClient<B>>, ClientError<B>> .

关于rust - future.then() 如何返回一个 Future?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/66254598/

29 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com