【问题标题】:Quick regex_search/replace, or clear indication of replacement?快速正则表达式搜索/替换,或明确的替换指示?
【发布时间】:2021-05-12 12:01:20
【问题描述】:

我必须浏览字符串集合以替换模式并保存更改。
保存操作(非常)昂贵且不在我的控制范围内,所以我想事先知道替换是否有任何作用。

我可以使用std::regex_search 来了解模式在我的输入中是否存在,并使用捕获组将详细信息存储在std::smatch 中。 std::regex_replace 似乎没有明确告诉我它是否做了任何事情。

模式和字符串任意长且复杂;在regex_search 之后运行regex_replace 似乎很浪费。
我可以直接比较输入和输出来寻找差异,但这也很不舒服。

是否有一种简单的方法来观察regex_replace 以确定其影响,或者使用由regex_search 填充的smatch 来进行更快的替换操作?

提前致谢。

【问题讨论】:

  • 字符串有多长?并且是替换长度相同还是长度不同?
  • @rustyx 大多数将在 256 个字符以下,但它们可以任意长。替换是任意的,我不能保证长度会不同。

标签: c++ regex c++11 replace


【解决方案1】:

不,regex_replace 不提供此信息,是的,您可以使用 regex_search 循环来提供此信息。

例如这样:

std::regex pattern("...");
std::string replacement_format = "...";
std::string input = "......"; // a very, very long string
std::string output, replacement;

std::smatch match;
auto begin = input.cbegin();
int replacements = 0;
while (std::regex_search(begin, input.cend(), match, pattern)) {
    output += match.prefix();
    replacement = match.format(replacement_format);
    if (match[0] != replacement) {
        replacements++;
    }
    output += replacement;
    begin = match.suffix().first;
}
output.append(begin, input.cend());

if (replacements > 0) {
    // process output ...
}

Live demo

【讨论】:

    【解决方案2】:

    由于regex_replace 创建了您的字符串的副本,您可以简单地将替换的字符串与原始字符串进行比较,如果它们不同,则仅“存储”新的字符串。

    对于 C++14,regex_replace 似乎返回了一个指向它最后写入位置的指针:

    https://www.cplusplus.com/reference/regex/regex_replace/ 版本 5 和 6 返回一个迭代器,它指向最后一个元素之后的元素 写入 out 所指向的序列的字符。

    【讨论】:

    • 字符串可能很长,因此比较是一种备用解决方案。不幸的是,我被 C++11 困住了。它也指向输出的结尾,但这并不意味着输出与输入有任何不同。
    • 根据替换,您可以依赖更改的字符串大小,这将是一个快速比较。
    猜你喜欢
    • 2019-11-03
    • 2013-06-14
    • 1970-01-01
    • 1970-01-01
    • 2018-05-25
    • 2011-07-09
    • 2010-11-25
    • 2010-10-30
    相关资源
    最近更新 更多