2012-01-17 2 views
1

У меня есть код, написанный на C, который я работаю над созданием библиотеки, из которой я могу обращаться к функциям с других языков.Использование стандартного вывода из библиотеки C в приложении C++

В настоящее время я пишу клиент C++ для этого кода, чтобы выяснить, какие изменения необходимы для обеспечения поддержки включения моей библиотеки в приложение на C++.

Как правило, двоичный код на основе C анализирует некоторый ввод, а затем выводит свои данные на stdout через ряд операторов fprintf.

Есть ли способ перенаправлять выходные данные из соответствующих функций C, отправленных на stdout?

Я не эксперт на C++, но я думаю, что я хотел бы предоставить подкласс буфера вывода потока C++ (ostream и ofstream?), Который содержит тот же результат, который в противном случае был бы отправлен соответствующим C функции: stdout.

Я хотел бы, если это возможно, перенаправить эти данные в поток файлов или на стандартный вывод в приложении C++.

Как я могу это сделать? Могу ли я оставить свой C-код как есть и перенаправить stdout из кода C++?

EDIT

Я могу редактировать функции C в вопросе, так что указатель файла или дескриптор является аргументом. Помогло бы, сможет ли он пройти туда, где идет выход? Для меня непонятно, как я перевел C++ IO и C IO. Я не могу передать в C++ iostream функции C, или я могу?

+0

В некоторых системах (особенно Linux) 'stdout' из C и' std :: cout' из C++ синхронизируются. И вы всегда можете использовать заголовок '' в коде на C++, чтобы получить понятие C 'stdout'. –

+0

Итак, если я устанавливаю 'FILE * fp = stdout' и имею функцию C' foo (FILE * fp) ', которая выплевывает данные в' stdout', то что бы я сделал, чтобы перенаправить вывод из 'std :: cout' в выходной поток, который либо (по-прежнему) 'std :: cout', либо поток вывода файла? –

+0

Функция C не знает о C++ 'std :: cout'! Но см. Http://gcc.gnu.org/onlinedocs/gcc-4.6.2/libstdc++/manual/manual/io_and_c.html –

ответ

0

Вам необходимо настроить pipe и запустить программу C как автономный процесс с его выводом, подключенным к входному концу трубы. Затем ваша программа на C++ должна считывать с выходного конца канала, а затем будет получать весь вывод из процесса C.

ОБНОВЛЕНИЕ: Я перечитываю вопрос немного больше после downvotes и комментариев. Я (сейчас) понимаю, что C-код работает как библиотека, т. Е. Связан с тем же исполняемым файлом, что и код C++.

Я не думаю, что вы можете принудительно перенаправить stdout для кода C, не влияя на выходной поток программы C++ в то же время, что кажется очень высокой ценой для того, чтобы иметь библиотеку.

Я все еще думаю, что решение заключается в «песочнице» кода C в собственном процессе с перенаправленным выходом, который затем можно прочитать по желанию. Разумеется, было бы лучше переписать функциональность C на return, вместо того, чтобы печатать их, но я предполагаю, что это не вариант.

Вы говорите, что код C использует fprintf(), то есть вариант с явным дескриптором файла, поэтому, возможно, вы можете использовать его и заставить его принять внешний вид FILE *, и в этом случае вы можете подавать ему трубку, подпроцесс.

Очень интересно видеть другие ответы, возможно, есть подход, который мне не хватает.

UPDATE 2: Если у вас есть возможность контролировать, какие FILE * вы передаете в библиотеку C, то это легко:

  • Чтобы иметь выход появляются с обычным выходом программы C++, просто передать в stdout.
  • Чтобы записать результат в файл, fopen() файл и передать полученный результат FILE *.

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

+0

Но Алекс Рейнольдс пишет о своей библиотеке C * *, а не о программе C! –

+0

Это не то, что мне нужно. Я пишу библиотеку, поэтому все это нужно делать в приложении. –

+0

** Выполнение программы C отдельно с помощью труб и сокетов не то, что я получаю. ** Я пишу ** библиотеку **, поэтому все это нужно делать с приложением. –

0

В комментарии я упоминал, что C++ std::cout и C stdout связаны в сложном пути, и что вы можете использовать stdout в C++, включив <cstdio>. Я также дал следующую ссылку: http://gcc.gnu.org/onlinedocs/gcc-4.6.2/libstdc++/manual/manual/io_and_c.html

Однако, возможно, вы захотите изменить API своей библиотеки и предоставить функции, которые записываются в поток, предоставленный пользователем, и/или в путь, указанный пользователем.

В Linux, вы также можете использовать open_memstream или fopencookie

0

Если я понял ваш вопрос правильно, нет, по крайней мере, со стандартным кодом конформного.

Что может быть связано с std :: ios_base :: sync_with_stdio, который гарантирует, что IO, созданный на некоторых потоках C++, правильно синхронизирован с IO make из потоков C. Таким образом, stdout синхронизируется с cout, stdin с cin и stderr width cerr. Но это не предназначено для изменения streambuf в cout и изменения, которые распространяются на stdout (как я понял ваш запрос), и я далеко не уверен в намеренном эффекте, если вы делаете freopen на stdout.

Смежные вопросы