我正在尝试执行一个Tk函数,该函数存储为哈希表中函数的引用。在下面这个非常简单的例子中,代码应该画一个大的红点(即按照第14行的操作)。我无法对createOval()进行有效引用,哈希表中没有$w->,也没有向下移动到第13行。我在谷歌上搜索过这个高点和低点,但都没有用。我错过了什么?
如果我治疗$w->。。。作为参考,错误消息是"错误的参数数量:…",如果我填充\\amp;在$w前面的第10行:"不是a11.pl第9行的CODE引用。">
这在Python中非常容易做到:只需将w.create_oval插入字典中,它就可以工作了。
use strict;
use warnings;
use Tk;
my $mw = MainWindow->new;
my $w = $mw->Canvas(-width => 1200, -height => 800);
$w->pack;
my %xfun = (
'b' => $w->createOval
);
$xfun{'b'}(200, 200, 250, 250, -fill=>'red');
#$w->createOval(200, 200, 250, 250, -fill=>'red');
MainLoop;
如果我处理$w->。。。作为参考,错误消息是"错误的参数数量:…">
我不知道你说的"当作参考"是什么意思。
您的代码不能像编写的那样工作,因为$w->createOval
是一个没有参数的方法调用,与$w->createOval()
相同。
对于&$w->createOval
,它解析为((&$w)->createOval)
,与($w->(@_)->createOval)
:(大部分)相同
- 将
$w
视为代码引用,并使用当前参数列表@_
调用它(这是发生错误的地方,因为$w
实际上是一个对象) - 获取返回值并对其调用
createOval
方法 - 参考
createOval
的返回值
您可以使用$w->can('createOval')
获得对createOval
子的引用,但这对您没有帮助,因为这只是函数(没有对象)。要调用它,您必须显式地传入$w
作为第一个参数(这在方法调用中隐式发生):
my %xfun = (
'b' => $w->can('createOval'),
);
$xfun{'b'}($w, 200, 200, 250, 250, -fill=>'red');
最直接的解决方案是b => sub { $w->createOval(@_) }
,即将方法调用封装在转发其参数的代理子中。
以下似乎有效:
use strict;
use warnings;
use Tk;
my $mw = MainWindow->new;
my $w = $mw->Canvas(-width => 1200, -height => 800);
$w->pack;
my %xfun = (
b => sub { $w->createOval(@_); },
);
$xfun{b}->(200, 200, 250, 250, -fill=>'red');
MainLoop;
注意:
我以为你原来的电话是
$xfun{'b'}(200, 200, 250, 250, -fill=>'red');
没有工作,因为它错过了作为第一个arg的对象$w
,但当我尝试将$w
显式传递为第一个参数:
$xfun{'b'}($w, 200, 200, 250, 250, -fill=>'red');
它仍然不起作用。。我得到错误:
wrong # args: should be ".canvas create oval coords ?arg arg ...?"