【发布时间】:2020-12-15 14:23:20
【问题描述】:
我正在努力将 Haskell 中的一个简单的 prolog 实现翻译成 Rust,以获得更多使用该语言的经验。
在 Haskell 中,我有一个类型类:
class Unifiable t v | t -> v where
variables :: t -> [v]
subs :: Unifier v t -> t -> t
unify :: t -> t -> (Maybe (Unifier v t))
我将其翻译成 Rust 中的以下特征:
pub type Unifier<V,T> = HashMap<V,T>;
pub trait Unifiable<T,V> {
fn variables(term: T) -> Vec<V>;
fn subs(unifier: Unifier<V,T>, term: T) -> T;
fn unify(firstTerm: T, secondTerm: T) -> Option<Unifier<V,T>>;
然后我定义了一个实用函数,只要Unifiable 的实例可用,我就可以使用它。作为初步定义,我使用了这个:
pub fn compose<V: Hash + Eq, T, U: Unifiable<T,V>>(first: Unifier<V,T>, other: Unifier<V,T>) -> Unifier<V,T> {
let unifier: Unifier<V,T> = first.iter().map(|(&x,y)| (x, U::subs(other, *y))).collect();
unifier.extend(other);
return unifier;
}
我打算类似于 Haskell 类型签名:
compose :: Unifiable v t => Unifier v t -> Unifier v t -> Unifier v t
问题是,我想在impl 块中为Unifiable 使用这个辅助函数compose,我不知道如何在调用站点引用Unifiable 实例:
impl <T: Eq, V: Clone + Eq + Hash> Unifiable<Term<T,V>,V> for Term<T,V> {
...
fn unify(firstTerm: Term<T,V>, secondTerm: Term<T,V>) -> Option<Unifier<V,Term<T,V>>> {
....
return Some(compose<V,Term<T,V>,X>(u, us));
....
}
...
}
问题是,我不知道X 使用什么来引用我当前定义的 impl 块中的 Unifiable 实例,如果我省略类型参数,我会得到“无法推断”类型参数”错误。这种带有特征的引用在 Rust 中是否可行?
【问题讨论】:
-
u和us是什么类型?如果您提供一个可以在Rust Playground 中运行的工作代码示例(即类型错误除外),将会有所帮助。