LogSumExp
,它适用于所有 Iterator<Item = f32>
和 Iterator<Item = f64>
我有自己的特征
FloatTrait
,它仅针对f32
和f64
实现,帮助我将程序中的特征界限保持在最低限度,但仍然对这两种类型具有通用性。
我想表达任何
Iterator<Item : FloatTrait> : LogSumExp
这有可能吗?
不,不可能表达“对于一个类型X
来实现
FloatTrait
,它也必须意味着所有
Iterator<Item=X>: LogSumExp
”。您可以通过在特征定义中使用
Self
子句来提供不直接在
where
上的附加约束,但要做您想要的事情将需要某种尚不存在的更高级的约束支持。
旧答案解决了不同的角度:
即使FloatTrait
没有实现超出
f32
和
f64
范围,编译器仍会假设可能存在其他实现。因此
FloatTrait
约束不仅仅是
f32
| 的别名。
f64
,因此
Iterator<Item: FloatTrait>: LogSumExp
不能仅仅因为
Iterator<Item = f32>: LogSumExp
和
Iterator<Item = f64>: LogSumExp
就被假定为真。为了获得这种行为,您必须精心设计您的实现,使其
确实涵盖所有FloatTrait
可能性(已知和未知)。你必须这样做,而不是单独的
impl
:
impl<I> LogSumExp for I where I: Iterator, I::Item: FloatTrait {
...
}
如果这听起来很愚蠢,因为不可能存在其他实现(由于是私有的,或密封的,或在二进制板条箱中),那么您并不孤单。实现和约束的孤儿规则和特征一致性是围绕板条箱之间的稳定可扩展性而设计的,这意味着它们是仅限本地板条箱的东西的眼中钉。