繁体   English   中英

在 Rust 中,是否可以从 ZC1C425268E68385F14ZA 中返回 static function?

[英]In Rust, is it possible to return a static function from a function?

假设我在 Rust 中有以下类型:

type UnOp = fn(u64) -> u64;

该类型允许我创建不同的一元操作:

const add1 : UnOp = |x| x + 1;
const mul2 : UnOp = |x| x * 2;

现在,假设我在代码的不同位置需要add2add3add4 (...) 来处理不同的数字。 编写所有定义会很麻烦,因此,我编写了一个通用adder function:

fn adder(add : u64) -> UnOp {
  |x| x + add
}

这将允许我为任何数字编写add(2)add(3)等:

// Prints 2 + 40
println!("result is: {}", adder(2)(40))

问题是: adder实际上是无效的 Rust 代码,因为|x|...是一个闭包,而不是 static function。 为了让adder按我的意愿工作,我需要将UnOp修改为闭包:

type UnOp = Box<dyn Fn(u64) -> u64>;

fn adder(add : u64) -> UnOp {
  Box::new(move |x| x + add)
}

问题是:如果我知道adder(N)的每次使用都应用于 static 值怎么办?

在这种情况下,创建动态闭包将是浪费的,计算方面的。 不仅如此, Box<dyn...>使代码变得非常复杂,甚至可能需要生命周期注解。 我的问题是:

是否可以在不修改UnOp的原始定义的情况下创建adder 也就是说,让UnOp成为 static function,而不是闭包?

从逻辑上讲,没有理由不可能,只要adder的 arguments 是 static,Rust 应该能够在每个特定的实例编译时扩展它。

您可以使用const Generics来做到这一点:

type UnOp = fn(u64) -> u64;


const fn adder<const ADD: u64>(x: u64) -> u64 {
    ADD + x
}

fn main() {
    let add_1: UnOp = adder::<1>;
    println!("{}", add_1(1));
}

操场

是否可以在不修改 UnOp 的原始定义的情况下创建加法器? 也就是说,让 UnOp 成为 static function,而不是闭包?

既然你没有解释为什么我会忽略这个要求。 因为我认为你限制了你的选择。

您可能更喜欢巧妙地使用泛型和特征:

trait UnOp {
    fn call(&self, _: u64) -> u64;
}

impl<F> UnOp for F
where
    F: Fn(u64) -> u64,
{
    fn call(&self, x: u64) -> u64 {
        self(x)
    }
}

fn adder(add: u64) -> impl UnOp {
    move |x| x + add
}

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM