将 cout 和 stdout 重定向到 C++ 中的字符串 用于单元测试

发布于 2024-07-28 23:03:20 字数 617 浏览 5 评论 0原文

我正在努力在单元测试下获取一些遗留代码,有时感知现有程序行为的唯一方法是从控制台输出。

我在网上看到很多关于如何将 stdout 重定向到 C++ 中的另一个文件的示例,但是有没有办法可以将其重定向到内存中的流,以便我的测试不必依赖于磁盘?

我希望将遗留代码发送到 stdout 的任何内容都转换为 std::string ,以便我可以轻松地在输出上查找。

编辑

遗留代码非常糟糕,以至于它使用了 cout << 的混合物。 ..printf。 这是我到目前为止所得到的:

void TestSuite::setUp(void)
{
    oldStdoutBuf = std::cout.rdbuf();
    std::cout.rdbuf(consoleOutput.rdbuf());
}
void TestSuite::tearDown(void)
{
    std::cout.rdbuf(oldStdoutBuf);
}

问题是这使用 printf 捕获输出。 我想要两者兼得的东西。 有任何想法吗?

I'm working on getting some legacy code under unit tests and sometimes the only way to sense an existing program behavior is from the console output.

I see lots of examples online for how to redirect stdout to another file in C++, but is there a way I can redirect it to an in-memory stream so my tests don't have to rely on the disk?

I'd like to get anything that the legacy code sends to stdout into a std::string so I can easily .find on the output.

Edit

The legacy code is so bad that it users a mixture of cout << .. and printf. Here is what I have so far:

void TestSuite::setUp(void)
{
    oldStdoutBuf = std::cout.rdbuf();
    std::cout.rdbuf(consoleOutput.rdbuf());
}
void TestSuite::tearDown(void)
{
    std::cout.rdbuf(oldStdoutBuf);
}

The problem is that this does not capture output using printf. I would like something that gets both. Any ideas?

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(4

成熟稳重的好男人 2024-08-04 23:03:20

std::stringstream 可能就是你的寻找。

更新
好吧,这有点 hack,但也许你可以这样做来获取 printf 输出:

char huge_string_buf[MASSIVE_SIZE];
freopen("NUL", "a", stdout);
setbuf(stdout, huge_string_buffer);

请注意,对于 linux,你应该使用“/dev/null”而不是“NUL”。 这将迅速开始填满巨大的字符串缓冲区。 如果您希望能够在缓冲区满后继续重定向输出,则必须调用 fflush(),否则它将引发错误。 有关详细信息,请参阅 std::setbuf

std::stringstream may be what you're looking for.

UPDATE
Alright, this is a bit of hack, but maybe you could do this to grab the printf output:

char huge_string_buf[MASSIVE_SIZE];
freopen("NUL", "a", stdout);
setbuf(stdout, huge_string_buffer);

Note you should use "/dev/null" for linux instead of "NUL". That will rapidly start to fill up huge_string_buffer. If you want to be able to continue redirecting output after the buffer is full you'll have to call fflush(), otherwise it will throw an error. See std::setbuf for more info.

温馨耳语 2024-08-04 23:03:20

您可以使用 freopen(..., stdout) ,然后将文件转储到内存或 std::string 中。

You can use freopen(..., stdout) and then dump the file into memory or a std::string.

深海夜未眠 2024-08-04 23:03:20

这可能是一种替代方案:

char bigOutBuf[8192];
char savBuf[8192];

fflush(stdout);
setvbuf(stdout,bigOutBuf,IOFBF,8192);//stdout uses your buffer

//after each operation
strncpy(savBuf,bigOutBuf,8192);//won't flush until full or fflush called

//...

//at long last finished
setbuf(stdout,NULL);//reset to unnamed buffer

这只是拦截缓冲的输出,因此仍然会转到控制台或任何地方。

希望这可以帮助。

This may be an alternative:

char bigOutBuf[8192];
char savBuf[8192];

fflush(stdout);
setvbuf(stdout,bigOutBuf,IOFBF,8192);//stdout uses your buffer

//after each operation
strncpy(savBuf,bigOutBuf,8192);//won't flush until full or fflush called

//...

//at long last finished
setbuf(stdout,NULL);//reset to unnamed buffer

This just intercepts the buffered output, so still goes to console or wherever.

Hope this helps.

萌梦深 2024-08-04 23:03:20

试试sprintf,效率更高。

int i;
char str[] = "asdf";
char output[256];
sprintf(output, "asdfasdf %s %d\n", str, i);

Try sprintf, that's more efficient.

int i;
char str[] = "asdf";
char output[256];
sprintf(output, "asdfasdf %s %d\n", str, i);
~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文