Перенаправить cout и stdout в строку в C++ для модульного тестирования

Я работаю над получением устаревшего кода в модульных тестах, и иногда единственный способ почувствовать поведение существующей программы - это вывод консоли.

В Интернете я вижу много примеров того, как перенаправить стандартный вывод в другой файл в C++, но есть ли способ, которым я могу перенаправить его в поток в памяти, чтобы мои тесты не зависели от диска?

Я хотел бы получить все, что унаследованный код отправляет в stdout, в std::string, чтобы я мог легко.find на выходе.

редактировать

Устаревший код настолько плох, что он использует смесь cout << .. а также printf, Вот что у меня так далеко:

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

Проблема в том, что это не захватывает вывод с использованием printf. Я хотел бы что-то, что получает оба. Есть идеи?

4 ответа

Решение

std::stringstream может быть то, что вы ищете.

ОБНОВИТЬ
Хорошо, это немного хак, но, возможно, вы могли бы сделать это, чтобы получить вывод printf:

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

Обратите внимание, что вы должны использовать "/dev/null" для linux вместо "NUL". Это быстро начнет заполнять огромный_строка_буффера. Если вы хотите продолжить перенаправление вывода после заполнения буфера, вам нужно вызвать fflush(), иначе он выдаст ошибку. Увидеть std::setbuf для получения дополнительной информации.

Ты можешь использовать freopen(..., stdout) а затем выгрузить файл в память или std::string,

Это может быть альтернативой:

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

Это просто перехватывает буферизованный вывод, так что все равно идет на консоль или куда угодно.

Надеюсь это поможет.

Попробуйте sprintf, это более эффективно.

int i;
char str[] = "asdf";
char output[256];
sprintf(output, "asdfasdf %s %d\n", str, i);
Другие вопросы по тегам