是否可以编写一个在迭代器上折叠的const函数?

时间:2019-04-02 16:10:51

标签: rust const

是否可以编写一个在迭代器上折叠的const函数?当我尝试时:

const fn foo(s: &str) -> u64 {
    return s.chars().fold(0, |accumulator, char| -> u64 {
        return accumulator ^ (char as u64);
    });
}

我收到一个编译器错误:

error: function pointers in const fn are unstable
 --> src/lib.rs:2:30
  |
2 |       return s.chars().fold(0, |accumulator, char| -> u64 {
  |  ______________________________^
3 | |         return accumulator ^ (char as u64);
4 | |     });
  | |_____^

我假定我的匿名函数|x, y| -> x { ... }作为函数指针传递到fold(),这就是导致错误的原因。

这里是否可以传递给fold的某种类型的const lambda,还是可以只使用for循环并将结果累加到一个可变变量中,然后从foo返回功能?我完全没有Rust的经验...

1 个答案:

答案 0 :(得分:4)

不,您不能在稳定的Rust 1.33中执行此操作。您需要将函数设为非常量:

fn foo(s: &str) -> u64 {
    s.chars().fold(0, |accumulator, char| {
        accumulator ^ (char as u64)
    })
}

请注意,我删除了明确的return关键字和闭包返回类型,这是惯用的。

另请参阅:


如果您在每晚的Rust中尝试这样做:

#![feature(const_fn)]

const fn foo(s: &str) -> u64 {
    s.chars().fold(0, |accumulator, char| {
        accumulator ^ (char as u64)
    })
}

您将收到其他错误:

error[E0015]: calls in constant functions are limited to constant functions, tuple structs and tuple variants
 --> src/lib.rs:4:5
  |
4 |     s.chars().fold(0, |accumulator, char| {
  |     ^^^^^^^^^

error[E0015]: calls in constant functions are limited to constant functions, tuple structs and tuple variants
 --> src/lib.rs:4:5
  |
4 | /     s.chars().fold(0, |accumulator, char| {
5 | |         accumulator ^ (char as u64)
6 | |     })
  | |______^

调用Iterator::fold需要对the original const fn RFC 911进行一些扩展。例如,原始RFC明确禁止使用它:

  

特征,特质实现及其方法不能为const

由于闭包是作为由特征支持的泛型实现的,所以我没有立即看到由于相同的原因可以很容易地实现闭包。