繁体   English   中英

将 Rc 作为函数参数传递时出错

[英]Error when passing Rc as a function argument

Rc<dyn Trait>作为函数参数传递时,我面临一些奇怪的行为。 下面的代码演示了这个问题。

use std::rc::Rc;

trait Trait {}

struct Struct {}

impl Trait for Struct {}

fn function(_t: Rc<dyn Trait>) {}

fn main() {
    let n = Rc::new(Struct {});

    // ok
    let r = Rc::clone(&n);
    function(r);

    // error, why?
    // function(Rc::clone(&n));
}

如果我将Rc存储在临时变量中,则一切正常。 但是,如果我尝试在函数调用中直接调用Rc::clone则会出现以下错误。

   |
19 |     function(Rc::clone(&n));
   |                        ^^ expected trait object `dyn Trait`, found struct `Struct`
   |
   = note: expected reference `&std::rc::Rc<dyn Trait>`
              found reference `&std::rc::Rc<Struct>`

Struct实现Trait 为什么我会收到这个错误?

这基本上只是类型推断规则的一个皱纹。 为了调用Rc::clone(&n) ,编译器必须知道Rc的类型参数是什么。

let r = Rc::clone(&n);
function(r);

在第一行,编译器看到Rc::clone是用&Rc<Struct>类型的参数调用的。 它可以为r自由选择类型,因此它推断被调用的函数应该是Rc::<Struct>::clone并且r也是Rc<Struct> 移到下一行,调用function(r)只是将r 强制转换Rc<dyn Trait>

function(Rc::clone(&n));

这里编译器再次必须为Rc选择一个类型参数,但它没有完全的自由:它必须选择可以传递给function东西。 所以它假设类型参数是dyn Trait ,因为Rc<dyn Trait>function期望的。

但是,您不能调用Rc::<dyn Trait>::clone(&n) ,因为虽然Rc<Struct>可以被强制为Rc<dyn Trait> ,但强制不能通过引用传递(您不能强制&Rc<Struct>&Rc<dyn Trait> )。 所以强制不能在Rc::clone(...)调用中发生。

您可以通过使用 turbofish 将类型参数指定为Struct来编译单行版本:

function(Rc::<Struct>::clone(&n));

或者通过添加显式强制转换来暗示编译器它不应该从它作为function参数的位置推断类型:

function(Rc::clone(&n) as _);

n.clone()也有效,因为. 对类型参数毫无疑问:它总是会找到Rc::<Struct>::clone因为自动解引用只查看接收器类型( n的类型)而不关心表达式的上下文。

有关的

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM