1

下面是两段代码。一个有效,一个无效,我想知道为什么。对于缺少评论和糟糕的变量名,我提前道歉,但现在这种语言真的让我很吃力。

// File1.cpp (contains relevant includes)
// Works! It writes to out.txt and appears to use in.txt correctly
int main(int argc, char* argv[]) {
    int num;
    std::ifstream in("in.txt");
    std::streambuf* cinbuf = std::cin.rdbuf();
    std::cin.rdbuf(in.rdbuf());

    std::ofstream out("out.txt");
    std::streambuf* coutbuf = std::cout.rdbuf();
    std::cout.rdbuf(out.rdbuf());

    cout << "Give me a number: ";
    cin >> num;

    std::cin.rdbuf(cinbuf);
    std::cout.rdbuf(coutbuf);

    return 0;
}

// File2.cpp (contains relevant includes)
// Does not work! Outputs nothing to out.txt.
class TestWithStdIO {
        std::streambuf* cinbuf;
        std::streambuf* coutbuf;
    public:
        TestWithStdIO(const char* inFile, const char* outFile) {
            std::ifstream in(inFile);
            cinbuf = std::cin.rdbuf();
            std::cin.rdbuf(in.rdbuf());

            std::ofstream out(outFile);
            coutbuf = std::cout.rdbuf();
            std::cout.rdbuf(out.rdbuf());
        }
        ~TestWithStdIO() {
            std::cin.rdbuf(cinbuf);
            std::cout.rdbuf(coutbuf);
        }
};

int main(int argc, char* argv[]) {
    int num;
    TestWithStdIO* ioTest = new TestWithStdIO("in.txt", "out.txt");
    cout << "Give me a number: ";
    cin >> num;
    delete ioTest;

    return 0;
}
4

2 回答 2

1

TestWithStdIO::TestWithStdIO()中, 指向的流缓冲区in.rdbuf()连同in(即在构造函数的末尾)一起被销毁。

于 2013-10-21T11:08:48.307 回答
1

std::[io]fstreams inand在构造函数中具有out本地范围(或自动存储持续时间) 。TestWithStdIO它们在函数结束时被销毁(并且文件被关闭),以及它们包含的缓冲区,在函数的末尾留下悬空指针cincout.

考虑改为制作inout的成员TestWithStdIO,如下所示:

class TestWithStdIO {
        std::streambuf* cinbuf;
        std::streambuf* coutbuf;

        std::ifstream in_;  // <-- member
        std::ofstream out_; // <-- member
    public:
        TestWithStdIO(const std::string& inFile, const std::string& outFile) :
            in_(inFile), out_(outFile) // <-- initializer list
        {
            cinbuf = std::cin.rdbuf();
            std::cin.rdbuf(in_.rdbuf());

            coutbuf = std::cout.rdbuf();
            std::cout.rdbuf(out_.rdbuf());
        }
        ~TestWithStdIO() {
            std::cin.rdbuf(cinbuf);
            std::cout.rdbuf(coutbuf);
        }
};

如果您只有支持,您可能需要in(inFile.c_str())和等价物。outC++03

另外,正如评论中所指出的,没有必要动态分配TestWithStdIO实例,实际上它很可能是错误的来源。做就是了

TestWithStdIO ioTest ("in.txt", "out.txt");
于 2013-10-21T11:25:34.890 回答