remove_if 的 C++ 意外行为

标签 c++ string stl-algorithm

我正在尝试使用 std::remove_if从一个简单的字符串中删除空格,但我得到了奇怪的结果。有人可以帮我弄清楚发生了什么吗?

该代码是:

#include <iostream>
#include <algorithm>
#include <string>

int main(int argc, char * argv[])
{
    std::string test = "a b";
    std::remove_if(test.begin(), test.end(), isspace);
    std::cout << "test : " << test << std::endl; 

    return 0;
}

我希望这可以简单地打印出来:
test : ab

但相反我得到
test : abb

尝试使用另一个字符串,我得到:

输入:“a bcde uv xy”

输出:“abcdeuvxy xy”

似乎它复制了最后一个“单词”,但有时会添加一个空格。我怎样才能让它删除所有空格而不做奇怪的事情?

最佳答案

std::remove_if 通过移动元素执行移除;实际上,删除的元素不会从容器中删除。 STL 算法没有这样的特权;只有容器可以移除它们的元素。

(强调我的)

Removing is done by shifting (by means of move assignment) the elements in the range in such a way that the elements that are not to be removed appear in the beginning of the range. Relative order of the elements that remain is preserved and the physical size of the container is unchanged. Iterators pointing to an element between the new logical end and the physical end of the range are still dereferenceable, but the elements themselves have unspecified values (as per MoveAssignable post-condition). A call to remove is typically followed by a call to a container's erase method, which erases the unspecified values and reduces the physical size of the container to match its new logical size.



您可以erase之后删除的元素(称为erase-remove idiom)。
test.erase(std::remove_if(test.begin(), test.end(), isspace), test.end());

关于remove_if 的 C++ 意外行为,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/59098518/

相关文章:

c++ - 两个应用程序同名 - 只是更改一个 .C 文件名?

c++ - Visual Studio C++ 数据结构错误, "link1120"

c++ - 为什么我的指针输出一个字符串而不是 C++ 中的内存地址?

NetBSD '::system' 上的 C++ 编译错误尚未声明

c++ - 使用 std::accumulate 和 std::string 有效

c - 对变量的赋值在完全不相关的函数中给出了段错误

perl - 为什么 Perl 是大多数字符串操作任务的最佳选择?

java - 从Java中的输入获取字符串

algorithm - 使用 STL 运行长度使用 std::adjacent_find 对字符串进行编码

c++ - std::equal_range 提示 "sequence not ordered"