LINUX.ORG.RU

sleep, файлы или как передавать данные из php в c++ бинарник

 , , ,


0

3

Доброе времени суток
как бы вы решали задачу
максимально просто передать текст «123»
из php на локалхосте в с++ бинарник на локалхосте
пробовал через http, но оно не стабильно работает
решил навелосипедить через файлы, родил такой код
он ждёт пока php создаст входной файл, затем он читает из него строку и удаляет файл и снова ждёт

оно конечно работает, но эти слипы сьедают cpu на переключениях контекста если этот код запускать многоразово....

как вы сделали вечный забор строк из файла без слипов?
или какой способ передачи «123» из php в с++ бинарник выбрали бы вы?

while (true) {

ifstream number_file("number_file");

if (!number_file){
std::this_thread::sleep_for(std::chrono::milliseconds(10));
number_file.close();
continue; }

getline(number_file, number);

if ((number.empty()) {
std::this_thread::sleep_for(std::chrono::milliseconds(10));
continue; }  


////////////some actions
std::remove("number_file");
std::this_thread::sleep_for(std::chrono::milliseconds(10));
}

★★★★★

Ответ на: комментарий от cobold

он ждёт пока php создаст входной файл, затем он читает из него строку и удаляет файл и снова ждёт

Похоже, что тогда бы php ушёл бы спать на втором запросе, пока файл всё ещё существует на диске.

gag ★★★★★
()
Ответ на: комментарий от firkax

php внутри вебсервера это какая-то чушь, пахнет апачем.

он именно из веб сервера пытается выдать данные

потому как

из php на локалхосте в с++ бинарник на локалхосте

пробовал через http, но оно не стабильно работает

решил велосипедить через файлы

то есть файлы - уже кривое решение которое никак не исправить

MKuznetsov ★★★★★
()
Ответ на: комментарий от smilessss

кроме файлов мне насоветовали более сложные решения

я пока буду смотреть в сторону блокирующего чтения с++

это самое проблемное решение которое возможно.

оно чревато например тем что ваш «php на локалхосте» будет переезжать на «не-локалхост». Тут сразу все потуги пойдут в корзину.

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

ну сделайте же сразу хорошо, возьмите midware - redis,mongo,memcashed. их для отчасти оттого и сделали, чтобы выезжать из песочницы не городя огород..

MKuznetsov ★★★★★
()
Ответ на: комментарий от sparks

Рисковый код, без проверок возвращаемых значений функций. На 10 тыс. процессах можно ведь влететь в /proc/sys/fs/file-max или ещё что, и потом долго разбираться, почему php снипет пишет «send», а на деле там ошибка какая...

mky ★★★★★
()
Ответ на: комментарий от Reset

Так или иначе в пайпах есть io, поскольку для него они и созданы, что даже в ультра оптимизированной версии в разы медленней zero copy на атомиках/busy loop, упирающегося в пропускную оперативки

ac130kz ★★
()
Ответ на: комментарий от smilessss

тебе - нельзя. А так - можно. Я вообще не понимаю, откуда слипы могут взяться. Если асинхронно, и нужно в промежутках между чтениями что-то делать, то возьми asio, или просто на коленке через select. Если синхронно: блокирующее чтение из пайпа и жди, когда тебе строчку пришлют. Будет просто, топорно и без слипов.

hatred ★★★
()
Ответ на: комментарий от Reset

Вобще не понятно, откуда взялась тема скорости передачи данных между процессами. ТС, вроде, не жаловался, его и передача через файл устраивала. Год назад у него было 7000 «бинарей», а сейчас 10000, прогресс налицо.

Но, ТС не описывает архитектуру его чуда в целом. Непонятно что у него делает php, кто запускает эти «c++ бинари». Сейчас он ещё собрался килять процессы, потребляющие 100% cpu, типа они плохие и не должны так делать. Возможно у него какой-то race и проц сжирается в цикле, спрятаном под:

//some actions
а не в sleep_for(std::chrono::milliseconds(10));.

mky ★★★★★
()
Ответ на: комментарий от smilessss

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

cobold ★★★★★
()

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

Вот тут примерчик есть с сервером и клиентом: ссылка #1 на opennet.ru

На сколько я понял, они так же обладают атомарными операциями для не больших порций данных: ссылка #2 на opennet.ru

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

PS. Плюс соглашусь с остальными, что архитектурно 10к процессов, которые должны все вместе быстро обрабатывать мелкие данные – это не про скорость и не про оптимальное использование процессора. Для достижения хороших скоростей в прикладных программах (user space) нужны специальные методы, включая буферизацию поступающей информации в «бОльшие» порции (например, через промежуточную БД в ОЗУ) и только затем передавать полученные порции на обработку. Иначе, у вас в любом случае все процессорное время съест межпроцессный обмен, нежели полезная работа.

Vic
()
Последнее исправление: Vic (всего исправлений: 3)
Ответ на: комментарий от Vic

Еще вариант, возможно вам подойдет обычная библиотека (dll-ка/so-шка), которую можете написать на Си, а из PHP просто вызывайте функцию либы для обработки.

Vic
()