我试图了解Trait::
和<T as Trait>::
方法调用语法的必要性。特别是,我正在查看this answer中的以下函数:
fn clone_into_array<A, T>(slice: &[T]) -> A
where
A: Default + AsMut<[T]>,
T: Clone,
{
assert_eq!(
slice.len(),
std::mem::size_of::<A>() / std::mem::size_of::<T>()
);
let mut a = Default::default();
<A as AsMut<[T]>>::as_mut(&mut a).clone_from_slice(slice);
a
}
似乎中间的两个方法调用行可以重写为:
let mut a = A::default();
a.as_mut().clone_from_slice(slice);
我相信这更具可读性,因为我们已经知道A
实现了Default
和AsMut<[T]>
,我们可以直接调用as_mut
作为方法,而不必通过明确a
。
但是,我错过了一个很好的理由,因为链接的答案更详细地写了吗?它被认为是好风格吗?在某些条件下两者在语义上是不同的吗?
答案 0 :(得分:1)
我同意你的重写 - 它们更清晰,是我推荐的功能。
我错过了一个很好的理由,因为链接的答案更详细地写了吗?
我的猜测是作者只是厌倦了写这个功能而停了下来。如果他们再看一遍,他们可能会把它改进得更短。
它被认为是好风格吗?
我认为除此之外,还有一般的社区风格偏好,除了一般&#34;短期更好,直到它不是&#34;。
在某些情况下两者在语义上是否不同?
他们不应该。
有时需要<>::
语法 ,否则它将是不明确的。一个例子from a recent question:
let array = <&mut [u8; 3]>::try_from(slice);
另一个时候,你没有一个名字很好的中间类型,或者中间类型在多个特征上是不明确的。一个gross example来自where
子句,但显示与表达式相同的问题:
<<Tbl as OrderDsl<Desc<Expr>>>::Output as LimitDsl>::Output: QueryId,
另见: