【问题标题】:Replace multiple pair of characters in string替换字符串中的多对字符
【发布时间】:2016-10-23 11:07:12
【问题描述】:

我想将所有出现的“a”替换为“b”,将“c”替换为“d”。

我目前的解决方案是:

std::replace(str.begin(), str.end(), 'a', 'b');
std::replace(str.begin(), str.end(), 'c', 'd');

是否可以使用 std 在单个函数中执行此操作?

【问题讨论】:

  • 查找正则表达式。您可以使用正则表达式将字母替换为一条语句。但是,它可能比您的 2 语句解决方案更复杂。

标签: c++ string c++11 std


【解决方案1】:

如果你不喜欢两次pass,你可以做一次:

 std::transform(std::begin(s), std::end(s), std::begin(s), [](auto ch) {
    switch (ch) {
    case 'a':
      return 'b';
    case 'c':
      return 'd';
    }
    return ch;
  });

【讨论】:

    【解决方案2】:

    棘手的解决方案:

    #include <algorithm>
    #include <string>
    #include <iostream>
    #include <map>
    
    int main() {
       char r; //replacement
       std::map<char, char> rs = { {'a', 'b'}, {'c', 'd'} };
       std::string s = "abracadabra";
       std::replace_if(s.begin(), s.end(), [&](char c){ return r = rs[c]; }, r);
       std::cout << s << std::endl;
    }
    

    编辑

    为了取悦所有效率激进的人,可以更改解决方案,不要为每个不存在的键附加rs 映射,同时保持棘手的味道不变。这可以按如下方式完成:

    #include <algorithm>
    #include <string>
    #include <iostream>
    #include <map>
    
    int main() {
       char r; //replacement
       std::map<char, char> rs = { {'a', 'b'}, {'c', 'd'} };
       std::string s = "abracadabra";
       std::replace_if(s.begin(), s.end(), [&](char c){ return (rs.find(c) != rs.end())
                                                            && (r = rs[c]); }, r); 
       std::cout << s << std::endl; //bbrbdbdbbrb
    }
    

    [live demo]

    【讨论】:

    • 只是备注:std::map::operator[] 如果给定键的对应值不存在,则新将默认构造元素附加到映射本身。所以使用@W.F 的这个解决方案,rs 的大小会随着不匹配字符的数量而增加。
    猜你喜欢
    • 2013-11-18
    • 1970-01-01
    • 2015-03-15
    • 2014-08-31
    • 1970-01-01
    • 2016-09-10
    • 1970-01-01
    • 2020-08-31
    相关资源
    最近更新 更多