现在我已经反转了字符串和正则表达式以使用正则表达式模拟 rfind。下面是一个示例程序:
#[static_init::dynamic]
// static r: Regex = regex::Regex::new(r"a\d").unwrap();
static r: Regex = regex::Regex::new(r"\da").unwrap();
let mut s = "123a123a456";
let sr = s.chars().rev().collect::<String>();
let option = r.find(&sr).unwrap();
let start = s.chars().count() - option.end();
let end = s.chars().count() - option.start();
println!("start: {:#?}", start);
println!("end: {:#?}", end);
如您所见,我必须将正则表达式从 a\d
反转为 \da
以及字符串 s
来模仿rfind
操作。有更容易的方法吗?谢谢。
最佳答案
regex-automata 有点支持这一点,而不必自己进行反转。我说“有点”是因为你必须自己把东西缝合在一起:
use regex_automata::{dense, DFA};
fn main() -> Result<(), Box<dyn std::error::Error>> {
let dfarev = dense::Builder::new()
.reverse(true)
.build_with_size::<u32>(r"a\d")?;
let dfafwd = dense::Builder::new()
.anchored(true)
.longest_match(true)
.build_with_size::<u32>(r"a\d")?;
let haystack = "123a123a456";
let mut at = haystack.len();
// This simple loop is wrong if the regex can match the empty string.
while let Some(start) = dfarev.rfind_at(haystack.as_bytes(), at) {
let end = dfafwd.find(haystack[start..].as_bytes())
.map(|i| start + i)
.expect("reverse match implies a forward match");
println!("match:{:?}:{:?}", (start, end), &haystack[start..end]);
at = start;
}
Ok(())
}
程序的输出是:
match:(7, 9):"a4"
match:(3, 5):"a1"
请注意,对于 regex-automata 0.1
,阅读 the section on differences between it and the regex crate 非常重要。主要区别在于 regex-automata 0.1 仅提供完全编译的 DFA。 (正则表达式自动机的下一版本将不仅限于完全编译的 DFA。)
关于regex - 如何在 Rust 中使用正则表达式从右侧查找?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/68931094/