Версия для печати темы
Нажмите сюда для просмотра этой темы в оригинальном формате
Форум программистов > Perl: Системное программирование > Совместное использование объектов в процессах


Автор: DProf 2.11.2012, 15:55
Возможно ли в PERLе такое межпроцессорное взаимодействие: возвращение объекта из дочернего процесса? Задача такая - параллельно крутятся процессы (полученные fork-ом) и каждый инициализирует и заполняет  данными объект(по объекту на процесс), который должен потом вернуться в родительский процесс для дальнейшей работы в родителе с объектами от детей. Совместное использование переменных в разных процессах очень простое - IPC::Shareable например. А вот сложные структуры так отработать не получается. Для демонстрации, например, надо вернуть объект Imager->new(), но вот тогда IPC::Shareable уже не работает:
Код

use warnings;use strict;use 5.10.1;
use IPC::Shareable;
use Imager;

my ($common, $bufer);
$common = tie $bufer, 'IPC::Shareable',  undef, {destroy => 1};

my $child = fork();

if ($child){
    print STDERR 'begin parent';
    waitpid($child,0);    
    print "--PARENT:\n\t\$common = $common_var\n\t\$bufer = $bufer\n";    
    print STDERR "parent exit\n";
}else{        
    print STDERR "begin child\n";
    $bufer = 'foo';
    #$bufer = Imager->new();# if no coment, this string write warn:
                            # Could not create semaphore set: No space left on device 
    print "--CHILD:\n\t\$common = $common_var\n\t\$bufer = $bufer\n";
    print STDERR "child exit\n";
}

exit;


Причем возвращать нужно именно объект, а не сами данные - просто передать их через pipe и потом заново в родителе инициализировать объект по этим данным можно, но это очень неэффективно по времени - не годится.

Как быть с совместным использованием объектов? В-принципе объекты для каждого процесса может инициализировать родитель и передавать детям ссылку, а в дочерних процессах эти объекты заполняются, но ведь даже так не работает:
Код

$common = tie $bufer, 'IPC::Shareable',  undef, {destroy => 1};
$bufer = Graphics::Magick->new();# Could not create semaphore set: No space left on device 


Perldoc и Camelbook не помогли... Я не очень хорошо разбираюсь в особенностях межпроцессорного взаимодействия - подскажите, возможно ли вообще то, что я хочу?
Спасибо, жду ответ.

Автор: Pfailed 2.11.2012, 18:44
http://www.perlmonks.org/?node_id=402290

Автор: DurRandir 2.11.2012, 22:45
Если коротко, то состояние объекта Imager - это не только перловые данные, но и состояние С-шной библиотеки. Его вы передать не сможете. Меняйте архитектуру - передавать между процессами объекты это странное желание, процессы для того и делаются, чтобы изолированно выполнить задачу от начала и до конца.

Автор: DProf 6.11.2012, 12:29
Спасибо за оперативный ответ.
DurRandir, согласен с Вами, сейчас так все и работает, процесс выполняет свою задачу, возвращает данные (картинку) через pipe и умирает. Беда лишь в том, что сначала в дочернем идет вызов Write (не самый быстрый), потом в родителе данные читаются (снова потеря времени) и снова инициализируется тот же объект, с которым идет дальнейшая работа (объекты от нескольких процессов соединяются и тд). Вот и хотелось не терять время сначала на печать картинки, а потом на инициализацию объекта по этой же картинке. Так что желание не совсем странное )

Автор: DProf 27.12.2012, 18:24
Кстати как вариант можно было использовать потоки (threads). Но там тоже проблемы есть.

Powered by Invision Power Board (http://www.invisionboard.com)
© Invision Power Services (http://www.invisionpower.com)