2010-09-18 98 views
2

mysub獲取子程序引用作爲其第一個參數。如何在調用Perl子例程時傳遞匿名子例程?

我可以簡單地打電話給mysub(sub{some subroutine body here})嗎?即在呼叫中定義一個匿名子程序?

語法是否正確(是否真的是傳遞給sub的引用)?

+4

你試過了嗎? – 2010-09-18 07:22:57

+2

我嘗試了它,它工作(否則我甚至不會問),但我記得我的歷史中的一些實例,當我測試了一些我在Perl中「發明」的東西,它似乎工作,但後來我發現它實際上工作只有特定的情況下,我有睾丸,我用的一般想法/語法是錯誤的...... :) – 2010-09-18 07:38:40

回答

8

當你嘗試過時發生了什麼?這無疑是測試這類工作是否有效的最佳方式。

但是,是的,該語法將工作得很好。

#!/usr/bin/perl 

use strict; 
use warnings; 

sub run_sub { 
    shift->(); 
} 

run_sub(sub { print "hello\n"; }); 
2

或者(通過@davorg答案),你可以使用:

sub run_sub 
{ 
    my($funcref) = @_; 
    &$funcref(); 
} 

更詳細的,當然;我想也是更清楚一點。但這是Perl - TMTOWTDI!

+0

'$ funcref - >()'是一個更現代的Perlish,但我認爲它們是完全相同的。 – Ether 2010-09-18 08:35:10

+1

它們不完全相同。 '&foo'(或者在這種情況下是'code $ foo')語法可以規避原型。 – 2010-09-18 09:42:23

+1

@Simon'&$ foo'和'$ foo - >()'都會繞過原型。從 http://perldoc.perl.org/perlsub.html#Prototypes:「原型對子程序引用(例如'\&foo')或間接子程序調用(例如'&{$ subref}'或'$ subref-> ()'「。 – FMc 2010-09-18 12:20:20

5

由於傳遞函數引用到其他子程序是一個相當普遍的模式,Perl中甚至有一些語法技巧,使它更順暢:

sub function1 {   # normal declaration, implicit `(@)` prototype 
    my $code = shift; 
    $code->(@_); 
} 

sub function2 (&@) {  # prototyped declaration 
    my $code = shift; 
    $code->(@_); 
} 

function1有被稱爲:function1 sub{...}, any_other_args

function2具有原型(&@),它告訴編譯器在第一個參數上施加子例程上下文(然後接受任意數量的附加參數)。

所以,你可以把它作爲function2 {...} any_other_args這反映了高階建宏像mapgrep,並sort把他們的代碼塊的方式。請注意,代碼塊之後沒有逗號,就像布丁一樣。

您可以在此處找到有關原型的更多信息:http://perldoc.perl.org/perlsub.html#Prototypes

請記住,Perl的原型是不是參數驗證,他們是提示編譯器,讓您編寫行爲類似於內建子程序。

相關問題