我正在尝试将一些C++代码迁移到Rust.我尝试了很多不同的方法,但没有一个编译.
我想要一个可以处理不同类型的通用模板,并且具有可调整的总大小和静态字段(const表达式)Capacity:
template<class KeyType, class ValueType, int PageSize>
struct BplusTreeLeaf {
static const uint16_t Capacity = (PageSize-16)/(sizeof(KeyType)+sizeof(ValueType));
KeyType keys[Capacity];
ValueType values[Capacity];
};
Run Code Online (Sandbox Code Playgroud)
我想从外面访问容量:
for(int i = 0; i < BplusTreeLeaf<x, y, 4096>::Capacity; i ++) { ... }
Run Code Online (Sandbox Code Playgroud)
似乎在Rust中没有办法做这样的事情,或者至少在我对Rust的理解中:
static 在结构中是不允许的,文档告诉我使用宏这是我得到的:
macro_rules! BplusTreeLeaf {
($KeyType:ident, $ValueType:ident, $PageSize:expr) => {
static Capacity_: u16 = ($PageSize - 16) / (std::mem::size_of::<$KeyType>() + std::mem::size_of::<$ValueType>());
struct BplusTreeLeaf_ {
keys: [$KeyType, ..Capacity_],
values: [$ValueType, ..Capacity_],
}
}
}
BplusTreeLeaf!(u64, u64, 4096)
Run Code Online (Sandbox Code Playgroud)
编译器产生"向量长度的预期常量expr",这是不正确的,因为我没有使用"mut" Capacity_,所以它必须是一个const表达式.即使它可以工作,Capacity_并且BplusTreeLeaf_仍然在全局范围/命名空间中.
我是否误解了Rust设计中的一些基本内容,或者这是不可能的?如果现在不可能,是否有计划作为未来的功能或者我应该继续使用C++ 11?
这个问题很老了,但仍然有效。您可以使用lazy_static箱。
普通静态变量必须使用常量表达式进行初始化,其中可能包括常量函数。这允许它们在编译时进行评估,并将其烘焙到二进制文件中。然而,这带来了许多限制,例如没有堆分配。
您希望在程序首次运行时评估该常量。就像这个例子一样,直接来自板条箱的页面:
lazy_static! {
static ref HASHMAP: HashMap<u32, &'static str> = {
let mut m = HashMap::new();
m.insert(0, "foo");
m.insert(1, "bar");
m.insert(2, "baz");
m
};
}
fn main() {
// First access to `HASHMAP` initializes it
println!("The entry for `0` is \"{}\".", HASHMAP.get(&0).unwrap());
// Any further access to `HASHMAP` just returns the computed value
println!("The entry for `1` is \"{}\".", HASHMAP.get(&1).unwrap());
}
Run Code Online (Sandbox Code Playgroud)