3

假设,大多数时候我有以下替换方案:

std::string line; // "line" contains a big string.
std::string from = "abcd";
std::string to = "xy";  // to.length() < from.length()
// replace "from" with "to" everywhere in "line"

在这里,string班级必须放置"xy"然后擦除 2 个字符,这有效地将所有字符line向左移动。在我的代码的整个生命周期中发生了很多这样的替换。

现在来到真正的问题。以下对我来说也是可以接受的:

// ...
if(to.legnth() < from.length())
  to.resize(from.length(), ' ');
// now to.length() = from.length()
// replace "from" with "to" everywhere in "line"

replace()仅当针对相同长度的字符串进行了优化时,上述练习才有帮助。应该是因为那是微不足道的;但只是想确认是否有人具有第一手知识。
我尝试通过 Eclipse IDE 浏览到字符串类,但无法深入研究。

4

1 回答 1

4

我只看 MSVC 2008 的实现。他们确实优化(我省略了一些东西):

_Myt& __CLR_OR_THIS_CALL replace(size_type _Off,
    size_type _N0, const _Myt& _Right, size_type _Roff, size_type _Count)
{
    ...
        if (_Count <= _N0)
        {   // hole doesn't get larger, just copy in substring
        _Traits_helper::move_s<_Traits>(_Myptr() + _Off, _Myres - _Off,
            _Myptr() + _Roff, _Count);  // fill hole
        _Traits_helper::move_s<_Traits>(_Myptr() + _Off + _Count, _Myres - _Off - _Count,
            _Myptr() + _Off + _N0, _Nm);    // move tail down
        }
    else if (_Roff <= _Off)
        {   // hole gets larger, substring begins before hole
        _Traits_helper::move_s<_Traits>(_Myptr() + _Off + _Count, _Myres - _Off - _Count,
            _Myptr() + _Off + _N0, _Nm);    // move tail down
        _Traits_helper::move_s<_Traits>(_Myptr() + _Off, _Myres - _Off,
            _Myptr() + _Roff, _Count);  // fill hole
        }
    else if (_Off + _N0 <= _Roff)
        {   // hole gets larger, substring begins after hole
        _Traits_helper::move_s<_Traits>(_Myptr() + _Off + _Count, _Myres - _Off - _Count,
            _Myptr() + _Off + _N0, _Nm);    // move tail down
        _Traits_helper::move_s<_Traits>(_Myptr() + _Off, _Myres - _Off,
            _Myptr() + (_Roff + _Count - _N0), _Count); // fill hole
        }
    else
        {   // hole gets larger, substring begins in hole
        _Traits_helper::move_s<_Traits>(_Myptr() + _Off, _Myres - _Off,
            _Myptr() + _Roff, _N0); // fill old hole
        _Traits_helper::move_s<_Traits>(_Myptr() + _Off + _Count, _Myres - _Off - _Count,
            _Myptr() + _Off + _N0, _Nm);    // move tail down
        _Traits_helper::move_s<_Traits>(_Myptr() + _Off + _N0, _Myres - _Off - _N0, _Myptr() + _Roff + _Count,
            _Count - _N0);  // fill rest of new hole
        }
        ...
    }

请注意,新长度较小的情况和长度相等的情况是相似的。

编辑:可以得出结论,在复制数据后字符串长度相同的情况下,必须移动/填充总共“0”个字符/孔(即不移动)。因此,实际上不需要优化,但它已经得到了微不足道的照顾。

于 2013-01-14T15:49:38.217 回答