`where`关键字的语法和语义是什么?

uru*_*ubi 20 rust

不幸的是,Rust的文档where非常缺乏.关键字仅出现在参考中的一个或两个不相关的示例中.

  1. where下面的代码会产生什么语义差异?有什么不同吗?哪种形式更受欢迎?

    fn double_a<T>(a:T) -> T where T:std::num::Int {
        a+a
    }
    
    fn double_b<T: std::num::Int>(a:T) -> T {
        a+a
    }
    
    Run Code Online (Sandbox Code Playgroud)
  2. 在CharEq特性的实现中,它似乎where被用作某种"选择器"来为匹配某种闭包类型的任何东西实现Trait.我对么?

有什么方法可以让我得到更好,更完整的图片where吗?(完整的使用和语法规范)

Lev*_*ans 21

在您的示例中,这两个代码严格相同.

where引入了这些子句以允许更具表现力的边界检查,例如:

fn foo<T>(a: T) where Bar<T>: MyTrait { /* ... */ }
Run Code Online (Sandbox Code Playgroud)

仅使用旧语法是不可能的.

where对于可读性,通常优选使用而不是原始语法,即使仍然可以使用旧语法.

你可以想象一下像这样的结构

fn foo<A, B, C>(a: A, b: B, c: C)
    where A: SomeTrait + OtherTrait,
          B: ThirdTrait<A>+ OtherTrait,
          C: LastTrait<A, B>
{
    /* stuff here */
}
Run Code Online (Sandbox Code Playgroud)

这种方式更易读,即使仍然可以使用旧语法表达.

关于特征的问题CharEq,代码是:

impl<F> CharEq for F where F: FnMut(char) -> bool {
    #[inline]
    fn matches(&mut self, c: char) -> bool { (*self)(c) }

    #[inline]
    fn only_ascii(&self) -> bool { false }
}
Run Code Online (Sandbox Code Playgroud)

它的字面意思是:CharEqF已经实现特征的所有类型实现特征FnMut(char) -> bool(即,一个闭包或一个函数接受char并返回一个特征bool).

有关更多详细信息,您可以查看引入该where子句的RFC :https://github.com/rust-lang/rfcs/pull/135

  • 来源...不,我不知道。我主要是通过查看几乎所有我看到的地方使用的 where 子句来假设它的。 (2认同)
  • 只是为了发泄一下,这个答案实际上是您将了解到多个 where 子句以逗号分隔的唯一地方!官方书籍、官方语言参考和 rust by example 对此都保持沉默,并且仅提供单一绑定的示例!因此,很容易陷入谷歌搜索的困境,直到找到与您要查找的内容相关的堆栈溢出答案。 (2认同)