попен перформанс в C - PullRequest
       32

попен перформанс в C

5 голосов
/ 10 февраля 2011

Я разрабатываю программу, которую планирую реализовать на C, и у меня есть вопрос о том, как лучше (с точки зрения производительности) вызывать внешние программы.Пользователь предоставит моей программе имя файла, а затем моя программа запустит другую программу с этим файлом в качестве входных данных.Моя программа затем будет обрабатывать вывод другой программы.

Мой типичный подход - перенаправить вывод другой программы в файл и затем сделать так, чтобы моя программа прочитала этот файл, когда это будет сделано.Однако я понимаю, что операции ввода-вывода довольно дороги, и я хотел бы сделать эту программу максимально эффективной.

Я немного посмотрел и нашел команду popen для запуска системных команд изахватить вывод.Как производительность этого подхода сравнивается с эффективностью подхода, который я только что описал?popen просто записывает вывод внешней программы во временный файл или сохраняет вывод программы в памяти?

В качестве альтернативы, есть ли другой способ сделать это, который даст лучшую производительность?

Ответы [ 5 ]

7 голосов
/ 10 февраля 2011

В системах Unix, popen будет передавать данные через канал в памяти. Если данные не выгружены, они не попадут на диск. Это должно дать вам почти такую ​​же высокую производительность, какую вы можете получить без изменения вызываемой программы.

2 голосов
/ 10 февраля 2011

Проблема с перенаправлением вашей подкоманды в файл заключается в том, что она потенциально небезопасна, в то время как popen связь не может быть перехвачена другим процессом.Кроме того, вам нужно убедиться, что имя файла уникально, если вы запускаете несколько экземпляров своей главной программы (и, следовательно, своей подкоманды).Решение popen от этого не страдает.

Производительность popen просто прекрасна, если вы не читаете / не записываете один байт.Всегда читайте / записывайте кратные 512 (например, 4096).Но это относится и к файловым операциям.popen связывает ваш процесс и дочерний процесс через каналы, поэтому, если вы не читаете, канал заполняется, а дочерний процесс не может писать, и наоборот.Таким образом, все обмененные данные находятся в памяти, но это только небольшие объемы.

2 голосов
/ 10 февраля 2011

1) popen сохранить вывод программы в памяти.На самом деле он использует каналы для передачи данных между процессами.

2) popen выглядит ИМХО как лучший вариант для производительности.

Он также имеет преимущество перед файлами уменьшения задержки.Т.е. ваша программа сможет получать вывод другой программы на лету, пока она производится.Если этот вывод велик, вам не нужно ждать, пока другая программа завершит обработку своих выводов.

2 голосов
/ 10 февраля 2011

popen делает в значительной степени то, что вы просите: он выполняет идиому pipe-fork-exec и дает вам указатель файла, из которого вы можете читать и писать.

Однако существует ограничение на размер буфера канала (~ 4K iirc), и, если вы не читаете достаточно быстро, другой процесс может заблокироваться.общая память как точка монтирования?[в системах Linux есть точка монтирования / dev / shm]

0 голосов
/ 10 февраля 2011

(при условии Unix или Linux)

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

popen подключается к другой программе по каналу, что означает, что вывод будет отправляться вашей программе постепенно Когда он генерируется, он копируется в вашу программу по частям.

...