Help fixing code

Why can’t I write:

pub struct TekPtr(pub Rc<dyn TekT>);

pub trait TekT {
    fn to_nbag(&self, tex_env: TekEnv) -> NestedBag;

    fn r(self) -> TekPtr {
        TekPtr(Rc::new(self))
    }
}

especially when I can do something like:

pub struct FooBar { ... }
impl TekT for FooBar {
  ...
    fn r(self) -> TekPtr {
        TekPtr(Rc::new(self))
    }
}

You need to add where Self: Sized bound to r

1 Like

Or declare trait TekT: Sized as a whole – traits default to ?Sized.

1 Like

Keep in mind that if you go with @cuviper’s solution, you will not be able to make a trait object from your trait. But it does make defining and implementing the trait much easier.

1 Like

@cuviper , @KrishnaSannasi : I am misunderstanding something very fundamental.

When I see Rc<dyn TekT>, I think “this is a ref-counted void* which satisfies TekT”

Where does the “:Sized” requirement come from?

Because Self defaults to ?Sized inside of trait objects. But, you can’t call Rc::new on unsized values, so you need theSized bound.

1 Like

Is this because RC consecutively in memory stores:

strong count, weak count, actual object (this part requires Size of Self)

This is because Rc needs to know how much memory to allocate, and only Sized types allow that have that info.

Also your own function takes a direct value, fn r(self), which needs to be Sized for codegen to work statically. There’s an unsized rvalues feature (RFC 1909, tracking issue) that will make this possible in some cases, e.g. passing parameters implicitly by-ref, but it’s not available yet.

1 Like