将 std::istringstream 作为参数传递不起作用



我刚刚开始学习c++ 11,我有这个头文件:

#pragma once
#include <string>
#include <fstream>
#include <sstream>
class Parser
{
public:
    Parser();
    ~Parser();
    void Parse(const std::string& path);
private:
    std::ifstream inFile;
    void LoadFile(const std::string& path);
    void Process(const std::istringstream& in);
};

和这个代码:

void Parser::LoadFile(const std::string& path)
{
    if (!Exists(path))
        throw std::exception("File not found.");
    else
    {
        inFile.open(path);
        std::string line;
        while (std::getline(inFile, line))
        {
            // Input stream.
            std::istringstream iss(line);
            Process(&iss);
        }
    }
}
void Parser::Process(const std::istringstream& in)
{
}

但是我在Process(&iss);行得到以下错误:

没有合适的构造函数可以从"std::istringstream *"std::basic_istringstream <char;std::>

我必须如何声明Process方法?

Process(&iss);

issstd::istringstream。当用于表达式&是地址运算符。

&iss表达式的结果是指向std::istringstreamstd::istringstream *的指针。

void Process(const std::istringstream& in);

声明该函数以const std::istringstream &的引用作为形参,而不是指针。

声明上下文中&表示引用类型

&在表达式或声明中使用时具有不同的含义。事实上,在表达式中,&可以完全表示其他含义,这取决于它出现的位置。

&字符在c++中有多种用途(有时非常令人困惑)。它可以用作位与操作符、寻址操作符,还可以在函数声明/定义中声明应通过引用传递给定形参

在您的示例中,声明void Process(const std::istringstream& in);是第三种情况—并且很好(可能使用const修饰符1除外)。然而,在Process(&iss);调用中,&是一个地址操作符,并且您试图将指针传递给iss变量(如果声明为void Process(const std::istringstream* in);,则可以)。

当一个函数被声明为通过引用接受参数时(就像你的Process一样),那么你只需要提供一个实际的变量/对象作为对该函数的任何调用的相应参数-编译器将为你提供引用。


1正如在评论中提到的,读取istringstream对象(可能)会修改它,因此const限定符可能会在您最不期望的时候破坏代码。(例如,只是在Process的主体中添加一些伪代码,如:int i; in >> i;将生成编译器错误;删除const限定符可以解决这个问题。)

最新更新