The first option is easiest. You can just implement the trait. Note that the Into::into accepts self, so you need to implement this for &Value not Value, otherwise the borrowed values would be referencing owned values that have been consumed by into and are already invalid.impl<'a> Into<Cow<'a, str>> for &'a Value { fn into(self) -> Cow<'a, str> { match self { Value::Float(f) => Cow::from(format!("{}", f.value).to_string()), Value::Text(t) => Cow::from(&t.value), } }}为&'a Value实施此操作可使我们将Cow<'a, str>中的生存期绑定到数据源.如果我们仅为Value实现这是不可能的,这很好,因为数据将消失!Implementing this for &'a Value lets us tie the lifetime in the Cow<'a, str> back to the source of the data. This wouldn't be possible if we implemented just for Value which is good because the data would be gone!一个更好的解决方案可能是在您的Text枚举中也使用Cow:An even better solution might be to use Cow in your Text enum too:use std::borrow::Cow;pub struct Text<'a> { pub value: Cow<'a, str>,}这将让您持有借来的&str:let string = String::From("hello");// same as Cow::Borrowed(&string)let text = Text { value: Cow::from(&string) };或String:// same as Cow::Owned(string)let text = Text { value: Cow::from(string) };由于Value现在可以间接保存引用,因此将需要它自己的生命周期参数:Since Value now can indirectly hold a reference, it will need a lifetime parameter of its own:pub enum Value<'a> { Float(Float), Text(Text<'a>),}现在Into<Cow<str>>实现可以用于Value本身,因为可以移动引用的值:Now the Into<Cow<str>> implementation can be for Value itself because referenced values can be moved:impl<'a> Into<Cow<'a, str>> for Value<'a> { fn into(self) -> Cow<'a, str> { match self { Value::Float(f) => Cow::from(format!("{}", f.value).to_string()), Value::Text(t) => t.value, } }}就像String一样,Cow<str>满足Deref<Target = str>的要求,因此只要传递引用,就可以在需要&str的任何地方使用它.这是为什么应始终尝试在函数参数中接受&str而不是String或.Just like String, Cow<str> satisfies Deref<Target = str> so it can be used anywhere that a &str is expected, by just passing a reference. This is another reason why you should always try accept &str in a function argument, rather than String or &String.通常,您可以像String一样方便地使用Cow,因为它们具有许多相同的impl.例如:Generally, you can use Cows as conveniently as Strings, because they have many of the same impls. For example:let input = String::from("12.0");{ // This one is borrowed (same as Cow::Borrowed(&input)) let text = Cow::from(&input);}// This one is owned (same as Cow::Owned(input))let text = Cow::from(input);// Most of the usual String/&str trait implementations are also there for Cowlet num: f64 = text.parse().unwrap(); 这篇关于如何在Rust中构建灵活的多类型数据系统而不克隆字符串?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持! 10-28 15:56