为什么我可以使用std :: vector <std :: ofstream *>而不是std :: vector <std :: ofstream>?

时间:2015-08-07 19:59:17

标签: c++ pointers vector ofstream

我有以下测试代码,其中我有一个参数fS,它是ofstream s的容器:

    #include <fstream>
    #include <vector>
    #include <cstdlib>
    #include <cstdio>

    int main()
    {
        // my container of ofstream(s)
        std::vector<std::ofstream> fS;

        // instantiate an ofstream
        std::ofstream of("myfile.txt");

        // push back to my container
        fS.push_back(of);

        return 0;
    }

根本不编译。而当我将ofstream的容器更改为指向ofstream的指针的容器时,代码编译:

    #include <fstream>
    #include <vector>
    #include <cstdlib>
    #include <cstdio>

    int main()
    {
        // my container of ofstream(s)
        std::vector<std::ofstream*> fS;

        // instantiate an ofstream
        std::ofstream * of = new std::ofstream("myfile.txt");

        // push back to my container
        fS.push_back(of);

        return 0;
    }

为什么会这样?

1 个答案:

答案 0 :(得分:2)

当您在push_back(of)上致电vector时,它会尝试将对象of的副本添加到矢量中。 (C ++喜欢复制东西)。在这种情况下,您尝试复制ofstream,但这是不允许的。直观地说,不清楚拥有ofstream副本意味着什么,所以规范禁止它。

另一方面,假设你有vector ofstream*个。现在,如果您尝试push_back指向ofstream的指针,那么C ++会将此解释为意味着您应该将指针的副本放入vector ,这很好,因为指针很容易被复制。

如果您有最近的编译器,那么第三种选择。 C ++最近引入了移动语义的想法,而不是试图文件流复制到向量中,您可以文件流移动到矢量。因此你可以这样写:

int main()
{
    // my container of ofstream(s)
    std::vector<std::ofstream> fS;

    // instantiate an ofstream
    std::ofstream of("myfile.txt");

    // push back to my container
    fS.push_back(std::move(of));

    return 0;
}

执行此操作后,变量of不再引用原始文件流;它反而只是有一些虚拟值。但是,该向量现在将有效地包含以前存储在of中的流。