在向量中使用STL的push_back函数添加字符串

3

我正在尝试将一个字符串推入一个字符串向量中,例如下面的代码:

void Node::set_val(string &val)
{
    this->val.push_back(val);
}

但是当我尝试按照以下方式调用它时:
Obj.set_val("10h;");

我遇到了以下错误:
error: no matching function for call to 'Node::set_val(const char [5])'

我假设双引号中的字符串与C++中的string相同,为什么会出现这样的错误?下面需要改变什么?

你的 set_val 函数期望一个指向 std::string 的引用作为参数。但是你只传递了一个包含5个字符的常量数组。 - Karthik Kalyanasundaram
@MertMertce 那只是为了解释,我是通过对象调用它的。 - Bharadwaj
3个回答

9

您正在以非常量引用的方式接收std::string。非常量引用无法绑定到右值,例如"10h;",因此您无法将文字传递给该函数。

如果您不打算修改参数,则应通过常量引用来获取参数:

void Node::set_val(const string &val)
//                 ^^^^^

这样,一个临时的std::string将从您的const char[5]构建,并传递给set_val。您可以通过按值接受string并将其movevector中来改进此操作:
void Node::set_val(string val)
{
    this->val.push_back(std::move(val));
}

这样可以避免您进行一些不必要的复制。


2

因此在C++中,const char*隐式转换为std::string,因为std::string有一个(非显式的)接受const char*的构造函数。所以编译器在这里尝试为您的函数调用创建一个临时的std::string对象,如下:

Node.set_val(std::string("10h;"));

然而,由于您声明了set_val的参数为一个非const引用std::string,编译器无法使此转换工作,因为临时对象不能绑定到非const引用。

有三种方法可以使其工作,具体取决于您想要实现什么:

void Node::set_val(const std::string& val) {}
void Node::set_val(std::string val) {}
void Node::set_val(std::string&& val) {}

所有代码都可以编译(最后一个需要C++11或更高版本),但考虑到你的用例,我建议使用第二个或第三个。想要了解原因,请尝试阅读一些有关C++11中移动语义的内容。

这里需要注意的重要事情是,const char* 通过创建临时对象隐式转换为std::string,而临时对象无法传递给接受非const引用的函数。


我不建议使用第三个选项,因为你无法将lvalue传递给它。 - TartanLlama
当然,你是正确的。我只是认为第三个选项更清晰地表明这是一个汇聚函数。不错,我只是假设它是一个汇聚函数,所以第二种情况实际上更加灵活。但还是感谢你指出来 :) - Mortano

0
你正在传递一个常量字符数组"10h;"
通过传递一个字符串来修复它:Obj.set_val(string("10h")); 并且编辑函数以按值接受一个字符串:
void Node::set_val(string val) { /* */ }

或者更好的方法是,编辑您的函数以接受一个const string&

void Node::set_val(const string &val) { /* */ }

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接