当我尝试acos(1)时,为什么Perl的Math :: Complex占用了这么多时间?

时间:2010-03-11 22:22:00

标签: perl profiler

在尝试配置我的Perl程序时,我发现Math::Complex占用了大量时间,看起来像某种警告。

另外,我的代码不应该生成或使用任何复杂的数字,所以我不知道它在Math :: Complex中做了什么。这是最昂贵的线路的FastProf输出:

/usr/lib/perl5/5.8.8/Math/Complex.pm:182 1.55480 276232: _cannot_make("real part",      $re) unless $re =~ /^$gre$/;
/usr/lib/perl5/5.8.8/Math/Complex.pm:310 1.01132 453641: sub cartesian {$_[0]->{c_dirty} ?
/usr/lib/perl5/5.8.8/Math/Complex.pm:315 0.97497 562188: sub set_cartesian { $_[0]->{p_dirty}++; $_[0]->{c_dirty} = 0;
/usr/lib/perl5/5.8.8/Math/Complex.pm:189 0.86302 276232: return $self;
/usr/lib/perl5/5.8.8/Math/Complex.pm:1332 0.85628 293660: $self->{display_format} = { %display_format };
/usr/lib/perl5/5.8.8/Math/Complex.pm:185 0.81529 276232: _cannot_make("imaginary part", $im) unless $im =~ /^$gre$/;
/usr/lib/perl5/5.8.8/Math/Complex.pm:1316 0.78749 293660: my %display_format = %DISPLAY_FORMAT;
/usr/lib/perl5/5.8.8/Math/Complex.pm:1335 0.69534 293660: %{$self->{display_format}} :
/usr/lib/perl5/5.8.8/Math/Complex.pm:186 0.66697 276232: $self->set_cartesian([$re, $im ]);
/usr/lib/perl5/5.8.8/Math/Complex.pm:170 0.62790 276232: my $self = bless {}, shift;
/usr/lib/perl5/5.8.8/Math/Complex.pm:172 0.56733 276232: if (@_ == 0) {
/usr/lib/perl5/5.8.8/Math/Complex.pm:316 0.53179 281094: $_[0]->{'cartesian'} = $_[1] }
/usr/lib/perl5/5.8.8/Math/Complex.pm:1324 0.48768 293660: if (@_ == 1) {
/usr/lib/perl5/5.8.8/Math/Complex.pm:1319 0.44835 293660: if (exists $self->{display_format}) {
/usr/lib/perl5/5.8.8/Math/Complex.pm:1318 0.40355 293660: if (ref $self) {   # Called as an object method
/usr/lib/perl5/5.8.8/Math/Complex.pm:187 0.39950 276232: $self->display_format('cartesian');
/usr/lib/perl5/5.8.8/Math/Complex.pm:1315 0.39312 293660: my $self  = shift;
/usr/lib/perl5/5.8.8/Math/Complex.pm:1331 0.38087 293660: if (ref $self) { # Called as an object method
/usr/lib/perl5/5.8.8/Math/Complex.pm:184 0.35171 276232: $im ||= 0;
/usr/lib/perl5/5.8.8/Math/Complex.pm:181 0.34145 276232: if (defined $re) {
/usr/lib/perl5/5.8.8/Math/Complex.pm:171 0.33492 276232: my ($re, $im);
/usr/lib/perl5/5.8.8/Math/Complex.pm:390 0.20658 128280: my ($z1, $z2, $regular) = @_;
/usr/lib/perl5/5.8.8/Math/Complex.pm:391 0.20631 128280: if ($z1->{p_dirty} == 0 and ref $z2 and $z2->{p_dirty} == 0) {

感谢您的帮助!

3 个答案:

答案 0 :(得分:5)

除非正则表达式匹配,否则第182和185行会发出警告。因此,缓慢可能不是输出警告而是进行正则表达式匹配。

如果探查器说这些行正在执行,那么它们就是。如果您没有直接调用它们,则加载的模块可能会间接调用它们。如果您使用更高级的分析器(例如Devel::NYTProf),您将能够看到调用图以确定代码的哪个部分最终导致调用缓慢的库代码。

答案 1 :(得分:4)

修改Math/Complex.pm并输入

use Carp;
Carp::cluck("in Math/Complex.pm");

围绕上面列出的一条线。这将打印出堆栈跟踪,您将看到如何进入此模块。

答案 2 :(得分:1)

根据perl调试器文档,您可以为INT信号设置处理程序。然后在它运行时你可以输入Ctrl-C,它将进入调试器。然后键入T以获得回溯,它应该显示它在Complex.pm代码中的确切原因。由于你在这段代码上花了很多时间,你可能会进入它,但如果你不这样做,那就再试一次,直到你这么做。