如何将正则表达式替换中捕获的模式转换为大写?

Abh*_*ckz 2 regex rust

我想替换/test/test1TEST1:.这就是我的开始:

extern crate regex; // 1.0.1

use regex::Regex;

fn main() {
    let regex_path_without_dot = Regex::new(r#"/test/(\w+)/"#).unwrap();

    let input = "/test/test1/test2/";

    // Results in "test1:test2/"
    let result = regex_path_without_dot.replace_all(input, "$1:");
}
Run Code Online (Sandbox Code Playgroud)

我试过用

let result = regex_path_without_dot.replace_all(&input, "$1:".to_uppercase());
Run Code Online (Sandbox Code Playgroud)

但我得到这个错误:

error[E0277]: the trait bound `for<'r, 's> std::string::String: std::ops::FnMut<(&'r regex::Captures<'s>,)>` is not satisfied
  --> src/main.rs:10:41
   |
10 |     let result = regex_path_without_dot.replace_all(&input, "$1:".to_uppercase());
   |                                         ^^^^^^^^^^^ the trait `for<'r, 's> std::ops::FnMut<(&'r regex::Captures<'s>,)>` is not implemented for `std::string::String`
   |
   = note: required because of the requirements on the impl of `regex::Replacer` for `std::string::String`
Run Code Online (Sandbox Code Playgroud)

我如何实现这个必需的特征?有一个简单的方法吗?

She*_*ter 5

Regex::replace 有签名

pub fn replace<'t, R: Replacer>(&self, text: &'t str, rep: R) -> Cow<'t, str>
Run Code Online (Sandbox Code Playgroud)

Replacer 实施方式:

  • &'a str
  • ReplacerRef<'a, R> where R: Replacer
  • F where F: FnMut(&Captures) -> T, T: AsRef<str>
  • NoExpand<'t>

没有实现String,这是您的错误消息的直接原因.您可以通过将您String转换为字符串切片来"修复"错误:

replace_all(&input, &*"$1:".to_uppercase()
Run Code Online (Sandbox Code Playgroud)

由于大写版本与小写版本相同,因此不会有任何改变.

然而,实施Replacer由封闭有用的:

let result = regex_path_without_dot.replace_all(&input, |captures: &regex::Captures| {
    captures[1].to_uppercase() + ":"
});
Run Code Online (Sandbox Code Playgroud)
replace_all(&input, "$1:".to_uppercase())
Run Code Online (Sandbox Code Playgroud)

这显示了理解此功能如何工作或功能优先级的基本错误.这跟说:

let x = "$1:".to_uppercase();
replace_all(&input, x)
Run Code Online (Sandbox Code Playgroud)

或者,等效地,因为1它是大写的1并且$是大写的$:

let x = String::from("$1:");
replace_all(&input, x)
Run Code Online (Sandbox Code Playgroud)

调用类似函数to_uppercase不会神奇地推迟到"稍晚点".