Rust 如何使结构只用于其内部常量?

Rust 如何使结构只用于其内部常量?,rust,constants,Rust,Constants,我需要将常量封装在Rust类型系统中。理想情况下,将准备就绪,但如果没有,并且由于我只需要一组有限的常量,我可以实现一些接近我需要的东西: trait U32Const{ 常数VAL:u32; } 结构U32Const10; U32Const10的impl U32Const{ 常数VAL:u32=10; } 结构MyType{ 瓦尔:u32, 模板:X, } impl MyType{ fn做某事(&self)->u32{ self.val*X::val } } fn main(){ 设a=MyT

我需要将常量封装在Rust类型系统中。理想情况下,将准备就绪,但如果没有,并且由于我只需要一组有限的常量,我可以实现一些接近我需要的东西:

trait U32Const{
常数VAL:u32;
}
结构U32Const10;
U32Const10的impl U32Const{
常数VAL:u32=10;
}
结构MyType{
瓦尔:u32,
模板:X,
}
impl MyType{
fn做某事(&self)->u32{
self.val*X::val
}
}
fn main(){
设a=MyType::{
瓦尔:20,
模板:U32Const10{},
};
println!(“{}”,a.do_something());
}
这会根据需要打印出
200
——也就是说,常量值来自
main
内部实例化时传入的类型

现在,这有点棘手,因为它需要在结构中创建一个
X
实例,我称之为
template
,然后它就没有使用,所以我得到了一个编译器警告

如果删除了
模板
字段,这是理想的API,那么编译器会抱怨
struct MyType
上有一个未使用的参数
X
。如果去掉
struct MyType
上的
X
参数,则在
impl
块中的
MyType
上会得到一个
意外类型参数


有什么方法可以让编译器满意吗?实际上,我想要一个只用于其内部
常量
的结构,而不是将幻影变量赋给结构,使用关联的类型可能会达到这个目的

trait U32Const{
U32型;
const VAL:Self::U32;
}
结构U32Const10;
U32Const10的impl U32Const{
U32型=U32型;
const VAL:Self::U32=10;
}
结构MyType{
val:X::U32,
}
impl MyType{
fn做某事(&self)->X::U32{
self.val*X::val
}
}
fn main(){
设a=MyType::{val:20};
println!(“{}”,a.do_something());
}

(对于多个const实现)

您可以通过声明
模板
具有以下类型来消除编译器警告:

使用std::marker::PhantomData;
性状U32Const{
常数VAL:u32;
}
结构U32Const10;
U32Const10的impl U32Const{
常数VAL:u32=10;
}
结构MyType{
瓦尔:u32,
模板:PhantomData::,
}
impl MyType{
fn做某事(&self)->u32{
self.val*X::val
}
}
fn main(){
设a=MyType::{
瓦尔:20,
模板:幻影数据,
};
println!(“{}”,a.do_something());
}


您仍然需要初始化它,但它不使用任何内存,如果您不使用它,编译器也不会抱怨。

有一个板条箱,它的功能与您完全相同,但我找不到它的名称RN@FrenchBoiethios你在想什么?是的!这不是你想要的吗?@FrenchBoiethios可能是的,我只是事先不知道,所以谢谢:)@FrenchBoiethios typenum是惊人的和超级强大的,只要你正确地搜索类型和特征边界。对于任何未来的读者,我建议阅读对我帮助很大的书籍。除了有多余的中间类型(编译器悄悄地接受它)之外,我不清楚区别是什么@Henrygomers所有的区别在于,您使用的泛型类型参数没有额外的模板字段,并且限制
val
的类型与
U32Const
的类型完全相同,从这一点来看,中间类型可能看起来并不多余,当然,如果您愿意限制它的话。是的,我可以看到使用了该类型,我只是不确定它为编译器提供了什么额外的信息来保持它的快乐。@HenryGomersall请阅读。
use std::marker::PhantomData;

trait U32Const {
    const VAL: u32;
}

struct U32Const10;
impl U32Const for U32Const10 {
    const VAL: u32 = 10;
}

struct MyType<X: U32Const> {
    val: u32,
    template: PhantomData::<X>,
}

impl<X: U32Const> MyType<X> {
    fn do_something(&self) -> u32 {
        self.val * X::VAL
    }
}

fn main() {
    let a = MyType::<U32Const10> {
        val: 20,
        template: PhantomData,
    };
    println!("{}", a.do_something());
}