添加运算符<<到std :: vector

时间:2013-03-23 20:18:31

标签: c++ vector

我想将operator<<添加到std::vector<string>。 这是运营商

std::vector<std::string>& operator<<(std::vector<std::string>& op, std::string str) {
    op.push_back(str);
    return op;
}

现在我可以通过这种方式向元素添加元素:

std::vector<std::string> vec;
vec << "aaa" << "bbb" << "ccc";

但是由于无法通过引用传递临时对象,因此未编译以下代码。

std::vector<std::string>() << "AAA" << "BBB";

如何更改代码以将元素添加到临时矢量?

我有一个接受const std::vector<std::string>&参数的函数,所以我想在一行中传递一个向量。

5 个答案:

答案 0 :(得分:2)

你做不到。 实现的唯一方法是,如果您的运算符是向量的成员。 (由于某种原因,可以在临时函数上调用成员函数。)

作为非成员函数,虽然你所追求的是不可能的

对于STL类型(如std :: vector)重载运算符也不是一个好主意。我认为你要完成的任务已经出现在boost assign库中。我不相信你能比他们更好地写出来,所以如果你需要的话,最好使用boost。

答案 1 :(得分:2)

我还没有真正考虑过这种情况的后果,但似乎你的rvalues可能会超载:

std::vector<std::string> operator<<(std::vector<std::string>&& op, std::string str) {
  op.push_back(std::move(str));
  return op;
}

是的,它按值返回,但由于§12.8/ 32,它将针对移动进行优化:

  

当满足或将满足复制操作的省略标准时,除了源对象是函数参数,并且要复制的对象由左值指定,重载决策以选择构造函数首先执行复制,就好像对象是由右值指定的一样。

答案 2 :(得分:1)

嗯......从技术上来说它是可行的但是风格很脏。仅仅是为了说明(我不太确定它值得真正实现)。检查使用GCC 4.7.2。我真的不知道这对常数对象会有什么影响。

#include <vector>
#include <string>
#include <iostream>

const std::vector<std::string>& operator << (const std::vector<std::string>& op, const std::string &str) 
{
    ((std::vector<std::string>&) op).push_back(str);
    return op;
}

int main()
{
    std::vector<std::string> a = std::vector<std::string>() << "A" << "B";
    a << "AAA";

    std::cout << "size: " << a.size() << std::endl;
    for (std::vector<std::string>::iterator i = a.begin(); i != a.end(); ++i)
    {
        std::cout << '\t' << *i << std::endl;
    }

    return 0;
}

答案 3 :(得分:0)

这是一个代码,可以帮助您做一些类似于您的想法的事情(http://ideone.com/3lrTxW):

#include <vector>
#include <string>

typedef std::string String;
typedef std::vector<String> StringVector;

class StringVectorWrapper {
    StringVector vector;
public:    
    operator StringVector&() {
        return vector;        
    }

    StringVectorWrapper& operator << (const String& str) {
        vector.push_back(str);
        return *this;
    }
};

使用的一个例子:

#include <iostream>    

void printVector(const StringVector& vector) {
    for(StringVector::const_iterator it = vector.begin(); it != vector.end(); it++)
        std::cout << *it << std::endl;
}

int main(void) {

    StringVectorWrapper w;
    w << "A" << "B";    
    printVector(w);

    printVector(StringVectorWrapper() << "Z" << "W");


    return 0;
}

但我不会在我的任何程序中使用这样的代码。

答案 4 :(得分:-1)

我担心这是不可能的。对任何标准库类重载操作符也是一个坏主意。 STL并不打算扩展。