类型错误调用存储在struct中的闭包

时间:2014-08-22 03:48:53

标签: closures typeerror rust

我最近开始尝试写一些生锈的玩具程序,我想我想要一个解析器组合器。 我天真的尝试是这样的:

enum ParseResult<T> {
    Ok(T),
    Error (String),
}

struct Parser<'a, I,O>{
    Parse: |I|:'a ->ParseResult<O>,
}
impl<'a, I,O,J> Parser<'a, I, O>{
    fn Compose<I,O,K>(self, RHS : Parser<O,K> )->Parser<I,K>{
        Parser
        {
            Parse :  |x:I|
               {
                   let intermediate = self.Parse;
                   match intermediate(x){ //mismatched types: expected `I` but found `I` (expected type parameter but found type parameter)

                       Ok(result) =>
                       {
                           let final = RHS.Parse;
                           final(result) mismatched types: expected `O` but found `0` (expected type parameter but found type parameter)

                       }          
                      Error(result) => Error(result)
                   }
               }
        }
    }
}

我很确定错误表明我的方法存在一些根本性的错误,但我不太确定是什么。

1 个答案:

答案 0 :(得分:2)

确实,您的计划中存在一些错误。

目前关闭是堆栈 - &#34;盒装&#34;,因此您无法从功能中返回它们,而这正是您示例中发生的事情 - 您正在存储关闭在Parser struct。

另一个错误是通用参数的错误使用。即使没有闭包,您的方法也无法工作:I方法上的OCompose参数与impl子句上的参数不同,即使它们具有相同的名称

顺便说一下,你不需要将一个闭包移到intermediate变量中。要调用存储在字段中的闭包,您需要执行以下操作:

let intermediate = (self.Parse)(x);

那就是说,几天前无箱封闭终于降落了。有了它们,你可以做你想做的事,虽然现在有些麻烦。

#![feature(unboxed_closures)]

struct Parser<I, O> {
    parse: Box<FnMut<(I,), Result<O, String>>>
}

impl<I, O> Parser<I, O> {
    fn compose<K>(mut self, mut rhs: Parser<O, K>) -> Parser<I, K> {
        Parser {
            parse: box |&mut: x: I| {
                match self.parse.call_mut((x,)) {
                    Ok(r) => rhs.parse.call_mut((r,)),
                    Err(e) => Err(e)
                }
            }
        }
    }
}

这个应该工作,但现在它doesn't,对我来说这看起来像个错误:

<anon>:11:23: 11:33 error: cannot borrow data mutably in an aliasable location
<anon>:11                 match self.parse.call_mut((x,)) {
                                ^~~~~~~~~~
<anon>:12:35: 12:44 error: cannot borrow data mutably in an aliasable location
<anon>:12                     Ok(result) => rhs.parse.call_mut((result,)),
                                            ^~~~~~~~~

当我用手动扩展的无盒装闭包重写这个例子时,它起作用了,所以这里确实存在一些编译器问题。无盒装的封闭是非常新的,所以这些事情并不出乎意料。我就此问题submitted an issue