g++;使用boost::algorithm:string:split和std::string的初始化错误无效 我正在把一些C++代码从Windows移植到Linux(最终是OSX)。由于Windows不符合,出现了大量的C++问题。我似乎已经克服了这一点,但现在面临一个提振问题

g++;使用boost::algorithm:string:split和std::string的初始化错误无效 我正在把一些C++代码从Windows移植到Linux(最终是OSX)。由于Windows不符合,出现了大量的C++问题。我似乎已经克服了这一点,但现在面临一个提振问题,c++,string,boost,C++,String,Boost,基本上,我想切碎一个字符串,其中感兴趣的子字符串用逗号分隔,然后将它们放入字符串向量中。这会导致g++中出现错误,但在visualstudio中编译时效果很好 该程序准确地说明了问题: #include <boost/algorithm/string.hpp> #include <string> #include <vector> int main (void) { std::vector<std::string> str_vec;

基本上,我想切碎一个字符串,其中感兴趣的子字符串用逗号分隔,然后将它们放入字符串向量中。这会导致g++中出现错误,但在visualstudio中编译时效果很好

该程序准确地说明了问题:

#include <boost/algorithm/string.hpp>
#include <string>
#include <vector>

int main (void) {


  std::vector<std::string> str_vec;
  std::string str_to_split = "this,is,the,string,to,split";

  boost::algorithm::split(str_vec,
                          str_to_split.substr(1, str_to_split.size()-2),
                          boost::algorithm::is_any_of(","),
                          boost::algorithm::token_compress_on);


  return 0;
}

此函数采用
std::string&
而不是
std::string
const std::string&
。这意味着您必须将
.substr
的结果存储在一个中间变量中,然后将该变量传递给
boost::algorithm::split
。无论如何,代码会更清晰


FWIW,我不知道为什么函数是这样设计的。对我来说似乎很奇怪,但你说对了。

这很清楚。Boost的第二个参数需要一个非常量引用(我想,它会修改它),而您不能将非常量引用绑定到临时参数。@SergeyA:我永远无法理解为什么它在这里需要一个非常量引用,或者为什么它会修改拆分函数的输入。@Barrythhatchet,也不知道,但是:
这个函数相当于C strtok
(来自Boost),并且
strtok
修改它的参数。可能有人刚刚复制了行为?@dmedine:因为这个原因,我的代码库中有一行“额外”的代码!不过,老实说,如果你用一个
str\u to\u split=str\u to\u split将要拆分的实际字符串设置为
str\u to\u split,可能会更清楚。substr(…)
@SergeyA:这是一个可怕的错误idea@SergeyA:你不认为本地修改Boost源是一件可怕的事情吗?@SergeyA:100%不可移植,一旦更新Boost,您的更改就会丢失,您正在干预您可能不完全理解的代码,您将如何对其进行版本控制(克隆整个Boost repo?ew)您可能会破坏您机器上构建的其他项目,等等。。。这不是修改或扩展第三方库的方法!如果您想包装
boost::algorithm::split
,那么就这样做,但是为了上帝的缘故,将新函数放在您自己的名称空间中!!在我的团队中,Boost代码模块不可能通过代码审查,除非它是完全、完全不可避免和非常临时的。@SergeyA对于您来说是允许MPL容器包含更多元素的正确方法
foo.cpp: In function 'int main()':
foo.cpp:11:54: error: invalid initialization of non-const reference type 'std::basic_string<char>&' from an rvalue of type'std::basic_string<char>'
   boost::algorithm::split(str_vec,str_to_split.substr(1, str_to_split.size()-2),boost::algorithm::is_an
                                                      ^
In file included from /usr/include/boost/algorithm/string.hpp:23:0,
                 from foo.cpp:1:
/usr/include/boost/algorithm/string/split.hpp:140:35: note:   initializing argument 2 of 'equenceSequenceT& boost::algorithm::split(SequenceSequenceT&, RangeT&, PredicateT, boost::algorithm::token_compress_mode_type) [with SequenceSequenceT = std::vector<std::basic_string<char> >; RangeT = std::basic_string<char>; PredicateT = boost::algorithm::detail::is_any_ofF<char>]'
         inline SequenceSequenceT& split(
                               ^