我有一个特点
trait Foo<T> : Iterator<Item=T> {
fn bar(&mut self) -> f64;
}
Run Code Online (Sandbox Code Playgroud)
我想一旦实现这种特质的类型T(在我的情况下f64在其所有引用类型() f64,&'a f64和&'a mut f64),因为在逻辑上也没关系.
我现在有
impl<T: Iterator<Item = f64>> Foo<f64> for T {
fn bar(&mut self) -> f64 {
// duplicated code
}
}
impl<'a, T: Iterator<Item = &'a f64>> Foo<&'a f64> for T {
fn bar(&mut self) -> f64 {
// duplicated code
}
}
impl<'a, T: Iterator<Item = &'a mut f64>> Foo<&'a mut f64> for T {
fn bar(&mut self) -> f64 {
// duplicated code
}
}
Run Code Online (Sandbox Code Playgroud)
有没有一个很好的方法来完成这个没有重复?
你可以使用这个Borrow特性.如果您查看文档页面中的实现者,前三个是相关的:它意味着f64,&'a f64并且&'a mut f64所有实现Borrow<f64>.您必须borrow在迭代器生成的每个值上调用该方法来获取&f64.
use std::borrow::Borrow;
impl<T> Foo<T::Item> for T
where T: Iterator,
T::Item: Borrow<f64>
{
fn bar(&mut self) -> f64 {
unimplemented!()
}
}
Run Code Online (Sandbox Code Playgroud)
顺便说一下,在特征上定义一个类型参数并同时在该类型参数和一个supertrait的相关类型之间设置一个约束是没有意义的.一个类型T只能有一个实现Iterator,因此它只能有一个实现Foo,尽管类型参数表明它可以实现许多不同的Foo<T>特性.因此,类型参数on Foo是完全冗余的(您可以只使用supertrait的关联类型而不是type参数).因此代码看起来应该更像这样:
use std::borrow::Borrow;
trait Foo: Iterator {
fn bar(&mut self) -> f64;
}
impl<T> Foo for T
where T: Iterator,
T::Item: Borrow<f64>
{
fn bar(&mut self) -> f64 {
unimplemented!()
}
}
Run Code Online (Sandbox Code Playgroud)
| 归档时间: |
|
| 查看次数: |
152 次 |
| 最近记录: |