【发布时间】:2018-08-18 15:14:02
【问题描述】:
我是 Rust 新手,在我的学习玩具项目中,我需要一个带有可变节点的图形数据结构,所以我想出了:
use std::cell::RefCell;
use std::clone::Clone;
use std::cmp::Eq;
use std::collections::HashMap;
use std::hash::Hash;
use std::rc::Rc;
pub trait Constructible<T> {
type C;
fn new(Self::C) -> T;
}
#[derive(Debug)]
pub struct HashedGraph<K: Eq + Hash + Clone, T: Constructible<T>> {
graph: HashMap<K, Rc<RefCell<T>>>,
}
impl<K, T> HashedGraph<K, T>
where
K: Eq + Hash + Clone,
T: Constructible<T>,
{
pub fn new<C>(connections: HashMap<K, C>) -> HashedGraph<K, T> {
let mut graph: HashMap<K, Rc<RefCell<T>>> = HashMap::new();
for key in connections.keys() {
graph.insert(
key.clone(),
Rc::new(RefCell::new(C::new(*connections.get(key).unwrap()))),
);
}
HashedGraph { graph }
}
}
impl Constructible<String> for String {
type C = String;
fn new(instring: String) -> String {
instring
}
}
fn main() {
let mut test = HashMap::new();
test.insert("one", "ONE");
test.insert("two", "TWO");
let hg = HashedGraph::new(test);
}
我的想法是,我希望节点可以从另一种数据类型构造,但该数据不包含在 Graph 中,因此是关联类型而不是泛型参数。节点 T 稍后将包含连接,它们只是指向其他节点的弱指针,但对于这个问题,这并不真正相关。编译时出现错误:
error[E0599]: no function or associated item named `new` found for type `C` in the current scope
--> src/main.rs:26:61
|
26 | graph.insert(key.clone(), Rc::new(RefCell::new( C::new( *connections.get(key).unwrap() ))));
| ^^^^^^ function or associated item not found in `C`
|
= help: items from traits can only be used if the trait is implemented and in scope
= note: the following trait defines an item `new`, perhaps you need to implement it:
candidate #1: `Constructible`
我不明白为什么constructible 的实现不在范围内或者还有什么不正确的。如果这是一种不习惯的实现方式,我会很高兴收到建议!
【问题讨论】:
-
C中的new<C>没有任何内容将其限制为Constructable。另外我认为您可以只使用Into/From而不是引入新特征,因为它看起来像转换。 -
另外,实现
String可能不是您的意思,因为您在主函数中使用了&str。 -
为什么
Constructible需要关联类型?类型参数T在您使用它的方式上似乎是多余的,可以只是Self。
标签: generics rust associated-types