2

I want to have a function that takes a function pointer of async fn.
What should the type of f be in fn run?

async fn foo() {}

fn run(f: /* ??? */) {}

According to the async/await RFC:

An async fn foo(args..) -> T is a function of the type fn(args..) -> impl Future<Output = T>.

However, if I write

fn run(f: fn() -> impl Future<()>)

I get the error message:

`impl Trait` not allowed outside of function and inherent method return types
Shepmaster
  • 388,571
  • 95
  • 1,107
  • 1,366
xxks-kkk
  • 2,336
  • 3
  • 28
  • 48

2 Answers2

3

You have to introduce two type parameters to your function signature, one for the Fn and one for the Future, e.g.

#![feature(futures_api, async_await)]

async fn foo() {}

fn run<G: std::future::Future, F: FnOnce() -> G>(f: F) {
    f();
}

fn main() {
    bar(foo)
}

You can replace FnOnce with Fn or FnMut depending on your needs.

Shepmaster
  • 388,571
  • 95
  • 1,107
  • 1,366
hellow
  • 12,430
  • 7
  • 56
  • 79
2

Using generic type parameter can help since an async fn returns an implementation of the Future trait.

#![feature(futures_api, async_await)]

use std::future::Future;

fn main() {
    run(foo);
}

async fn foo() {}

fn run<T: Future>(f: fn() -> T) {
    f();
}
Shepmaster
  • 388,571
  • 95
  • 1,107
  • 1,366
Ömer Erden
  • 7,680
  • 5
  • 36
  • 45