为什么我不能像trim_right_matches()一样在trim_matches()中使用& str?

时间:2018-04-16 11:41:28

标签: string rust pattern-matching

trim_right_matches我可以传递一个字符串值:

println!("{}", "[(foo)]".trim_right_matches(")]"));
// [(foo

但是,我不能在trim_matches中使用字符串值:

println!("{}", "[(foo)]".trim_matches("[()]"));

因为我收到以下错误:

error[E0277]: the trait bound `std::str::pattern::StrSearcher<'_, '_>: std::str::pattern::DoubleEndedSearcher<'_>` is not satisfied
 --> test.rs:2:27
  |
2 |     println!("{}", "[(foo)]".trim_matches("[()]"));
  |                              ^^^^^^^^^^^^ the trait `std::str::pattern::DoubleEndedSearcher<'_>` is not implemented for `std::str::pattern::StrSearcher<'_, '_>`
error: aborting due to previous error

以下代码有效:

println!("{}", "[(foo)]".trim_matches(&['(', '[', ']', ')'] as &[_]));
// foo

然而,它很长并且不像单个字符串值那样容易阅读;我希望能够使用与trim_right_matches类似的字符串值。

2 个答案:

答案 0 :(得分:5)

这两个功能有相似的签名,但是如果你仔细观察,你会注意到他们的搜索模式实际上是不同的:

trim_right_matches

pub fn trim_right_matches<'a, P>(&'a self, pat: P) -> &'a str
where
    P: Pattern<'a>,
    <P as Pattern<'a>>::Searcher: ReverseSearcher<'a> // ReverseSearcher

trim_matches

pub fn trim_matches<'a, P>(&'a self, pat: P) -> &'a str
where
    P: Pattern<'a>,
    <P as Pattern<'a>>::Searcher: DoubleEndedSearcher<'a> // DoubleEndedSearcher

the docs for DoubleEndedSearcher中,您可以找到&str无法成为DoubleEndedSearcher的原因:

  

(&str)::Searcher不是DoubleEndedSearcher,因为模式"aa"   在大海捞针"aaa"中匹配为"[aa]a""a[aa]",具体取决于   从哪一方搜索。

至于为什么你的解决方法有效:

"[(foo)]".trim_matches(&['(', '[', ']', ')'] as &[_]));

它是因为它实际上不匹配&str,而是&[char],它不是字符串切片而是一个字符数组的切片,这是一个有效的{ {1}}。

答案 1 :(得分:4)

第一部分代码并没有按照你的想法行事。它从末尾精确修剪字符串")]",但不会修改字符串"([foo])"。换句话说,将一个字符串传递给trim函数意味着&#34;完全修剪这个字符串&#34;,而不是&#34;修剪此字符串中出现的所有字符&#34;。没有编译的代码不会做你想要的,因为它只会删除确切的字符串"[()]",而且这不会出现在你的例子中。

传递一组字符而不是单独修剪所有字符,无论顺序如何。

所以你想要一个字符数组,即使传递一个字符串看起来更方便。

至于为什么你编写的代码没有编译,ljedrz回答了那一部分。