2
votes

I'm trying to create a trait(StringToTable) that return a struct with an implementation of another trait(Table).

When I have read this answer How to infer the return type of a function?, I tried the "boxed type" approach, but without success.

I don't know the struct type on call my StringToTable, so I can't use approaches like 'to_table< T >' or 'StringToTable< T >' ..

Playground with the error: https://play.rust-lang.org/?version=stable&mode=debug&edition=2018&gist=cac035a6e6357c204156fab13449e865

My code:

1° approach:

fn to_table(table: String) -> Option<Box<dyn Table<DeserializeOwned + Serialize + SearchIndex>>>;

I got:

error[E0225]: only auto traits can be used as additional traits in a trait object
  --> src/main.rs:18:75
   |
18 |     fn to_table(table: String) -> Option<Box<dyn Table<DeserializeOwned + Serialize + SearchIndex>>>;
   |                                                        ----------------   ^^^^^^^^^
   |                                                        |                  |
   |                                                        |                  additional non-auto trait
   |                                                        |                  trait alias used in trait object type (additional use)
   |                                                        first non-auto trait
   |                                                        trait alias used in trait object type (first use)

2° approach:

fn to_table2(table: String) -> Option<Box<dyn Table<T>>> where T: DeserializeOwned + Serialize + SearchIndex;

I got:

error[E0412]: cannot find type `T` in this scope
  --> src/main.rs:20:68
   |
20 |     fn to_table2(table: String) -> Option<Box<dyn Table<T>>> where T: DeserializeOwned + Serialize + SearchIndex;
   |                                                                    ^ not found in this scope

** My code has been simplified

What I'm trying to do: receive a random name on a tcp server and got the equivalent struct for it.

1

1 Answers

0
votes

In the second approach, you can fix the compilation error by declaring the type parameter T. You can do this on the function or on the trait.

On the function:

fn to_table2<T>(table: String) -> Option<Box<dyn Table<T>>> where T: DeserializeOwned + Serialize + SearchIndex;

On the trait:

pub trait StringToTable<T> where T: DeserializeOwned + Serialize + SearchIndex {

    fn to_table2(table: String) -> Option<Box<dyn Table<T>>>;
}

Another option is to use an associated type:

pub trait StringToTable {
    type T : DeserializeOwned + Serialize + SearchIndex;

    fn to_table2(table: String) -> Option<Box<dyn Table<Self::T>>>;
}