为什么在 Rust 中类型别名无法使用原始类型的关联常量?

3

编辑说明:从Rust 1.43版本开始,这个功能已经按预期工作。


我有一个类型别名type CardId = u64;,我想通过std::u64::MAX常量将它初始化为它所能拥有的最大值。但很惊讶地发现,我不能从别名直接实现。

use std::u64;

type CardId = u64;

fn main() {
    let this_works = u64::MAX;
    let this_doesnt_work = CardId::MAX;

    println!("Max amount in integer: {} and {}", this_works, this_doesnt_work);
}

(玩耍链接)

我原以为 MAX 常量也可以从类型别名中访问。当我将类型更改为 u32 时,这将有助于我,因为代码会有两个需要修改的点,而不仅仅是类型别名的位置。为什么要做出这个决定,我是否错过了某些可能使其成为可能的东西?

2个回答

8
在 Rust 1.43 之前,诸如 std::u64::MAX 的常量不是 u64 类型的关联常量,而是在名为 u64 的模块中定义的常量。这是 Rust 还没有关联常量时的遗留问题。
从 Rust 1.43 开始,这些常量被定义为相应类型的关联常量。目前有 一个 RFC 被开启来弃用这些模块。现在它们只是"软弃用",文档中指出:

Constant std::u32::MAX

pub const MAX: u32 = u32::max_value(); // 4_294_967_295u32

The largest value that can be represented by this integer type. Use u32::MAX instead.

(重点是我的)

另一种方法是使用相关的const方法(例如u32::max_value),因为在关联常量之前已经有了常量方法。这些方法也被软弃用,文档中注明:

pub const fn max_value() -> u32

This method is soft-deprecated.

Although using it won’t cause compilation warning, new code should use u32::MAX instead.

Returns the largest value that can be represented by this integer type.

(强调不是


关联常量也可以通过类型别名来访问,就像您所期望的那样:
struct Foo;

impl Foo {
    const FOO: u32 = 42;
}

type Bar = Foo;

fn main() {
    let this_works = Foo::FOO;
    let this_also_work = Bar::FOO;

    let this_works_too = u32::MAX; // As of Rust 1.43

    println!("The answer: {} and {} or {}", this_works, this_also_work, this_works_too);
}

(操场的永久链接)


7

这些信息已经过时,请参考mcartons的解答获得更好的解决方法。


这是因为std::u64::MAX是一个模块常量,而不是类型常量。

如果您想要使用它与类型别名一起使用,则可以使用max_value

use std::u64;

type CardId = u64;

fn main() {
    let this_works = u64::max_value();
    let this_does_work_as_well = CardId::max_value();
    
    println!("Max amount in integer: {} and {}", this_works, this_does_work_as_well);
}

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接