我有一個方法,它接受一些引數,從中創建(解密)一個中間值,并嘗試從該中間值構造一個型別實體。只要型別是固定的,它就可以正常作業。如果我想通過泛型支持多種型別,我會遇到麻煩。這是縮小的代碼:
impl Factory
{
pub fn get<'a, T>(&'a self, value: &'a str) -> T
where T: From<&'a str>
{
let value_parsed = value.chars().rev().collect::<String>();
return T::from(&value_parsed);
}
}
您可以在此處運行完整代碼。編譯產生以下錯誤:
31 | pub fn get<'a, T>(&'a self, value: &'a str) -> T
| -- lifetime `'a` defined here
...
35 | return T::from(&value_parsed);
| --------^^^^^^^^^^^^^-
| | |
| | borrowed value does not live long enough
| argument requires that `value_parsed` is borrowed for `'a`
36 | }
| - `value_parsed` dropped here while still borrowed
正如我所說,Item
在方法簽名中使用而不是泛型型別可以消除此錯誤。不傳遞對臨時值的參考T::from()
而是移動臨時值也是一種選擇,但考慮到value_parsed
它實際上并沒有在這里被消耗,它變得很尷尬并且與我的代碼庫的其余部分不一致。
有什么辦法可以確保value_parsed
壽命足夠長?或者是否有其他解決方案不在這里不使用參考?
uj5u.com熱心網友回復:
您將使用更高等級的特征系結來指示該型別T
可以由具有任何生命周期的值構成,而不是在函式上用作泛型時的特定生命周期:
pub fn get<T>(&self, value: &str) -> T
where T: for<'a> From<&'a str>
// ^^^^^^^
您之前所擁有的是表明T
可以從具有基于self
和的生命周期的參考構建value
,但是,由于value_parsed
是區域變數,因此對它的參考不能滿足該生命周期約束。
uj5u.com熱心網友回復:
原來使用我自己的特征在這里有效,不需要我在簽名中指定對型別的參考——因此不需要將生命周期與特征相關聯:
trait Get<T>
{
fn get(value: &T) -> Self;
}
使用此特征,該方法可以編譯:
pub fn get<'a, T>(&'a self, value: &'a str) -> T
where T: Get<String>
{
let value_parsed = value.chars().rev().collect::<String>();
return T::get(&value_parsed);
}
我不確定這是否是最佳解決方案,但此解決方案有效。
轉載請註明出處,本文鏈接:https://www.uj5u.com/yidong/470406.html
上一篇:TypeScript:是否可以定義一個接受不同型別引數的可變引數函式?
下一篇:實作介面的指標的泛型型別是什么?