這個簡單的摘錄,在 Perl 5.16.3 上運行,在開放的時候分叉了一個子行程,它將資料發送到主行程。
#!/usr/bin/perl
use Tk;
my $mainWindow = MainWindow->new();
$mainWindow->Button(-text => "Run", -command => \&run)->pack();
MainLoop;
my $fh;
sub receiver()
{
print "$_" while <$fh>;
print "End\n";
close $fh;
}
sub run()
{
print "run\n";
my $pid = open $fh, '-|';
die "Failed to start\n" unless defined $pid;
print "pid=$pid\n";
exec "echo Hello" unless $pid;
$mainWindow->fileevent($fh, 'readable', \&receiver);
}
它僅在第一次按預期作業,在第二次單擊打開的按鈕時:
Tk::Error: Can't locate object method "OPEN" via package "Tk::Event::IO" at fe.pl line 16. Tk callback for .button Tk:: ANON at /usr/lib64/perl5/vendor_perl /Tk.pm 第 251 行 Tk::Button::butUp 在 /usr/lib64/perl5/vendor_perl/Tk/Button.pm 第 175 行(命令系結到事件)
我正在努力理解原因,但沒有成功。任何的想法?
uj5u.com熱心網友回復:
Tk::Error: 無法通過包“Tk::Event::IO”定位物件方法“OPEN”
似乎您fileevent每次完成后都需要洗掉處理程式receiver,否則Tk稍后將嘗試再次呼叫回呼(使用您剛剛在接收器中關閉的相同檔案句柄)但是檔案句柄不再有效。
以下對我有用:
use strict;
use warnings;
use Tk;
my $mainWindow = MainWindow->new();
$mainWindow->Button(-text => "Run", -command => \&run)->pack();
MainLoop;
sub run()
{
my $fh;
my $receiver = sub {
print "$_" while <$fh>;
print "End\n";
close $fh;
# delete handler since $fh is no longer used
$mainWindow->fileevent($fh, "readable", "");
};
print "run\n";
my $pid = open $fh, '-|';
die "Failed to start\n" unless defined $pid;
print "pid=$pid\n";
exec "echo Hello" unless $pid;
$mainWindow->fileevent($fh, 'readable', $receiver);
}
uj5u.com熱心網友回復:
#!/usr/bin/perl
use Tk;
my $mainWindow = MainWindow->new();
$mainWindow->Button(-text => "Run", -command => \&run)->pack();
MainLoop;
sub run()
{
my $fh;
my $pid;
$SIG{CHLD} = sub
{
my $kid = waitpid(-1, WNOHANG);
print "$kid exited with $? ${^CHILD_ERROR_NATIVE}\n"
};
my $receiver = sub
{
print "$_" while <$fh>;
print "End\n";
close $fh;
# delete handler since $fh is no longer used
$mainWindow->fileevent($fh, 'readable', '');
};
print "run\n";
$pid = open $fh, '-|';
die "Failed to start\n" unless defined $pid;
print "pid=$pid\n";
exec "echo Hello" unless $pid;
$mainWindow->fileevent($fh, 'readable', $receiver);
}
轉載請註明出處,本文鏈接:https://www.uj5u.com/yidong/425539.html
