2010-06-13 47 views
7

我剛剛開始使用PHP設置一個匿名函數,我想知道如果有一個匿名函數添加到一個類實例的方法。PHP的一個實例

例如,讓我們說......

class A{ 
    public B; 
} 

$c = new A(); 

//This is where I am getting a little confused... 
//The following wont work 

$c->B = function(){echo('HelloWorld');}; 
$c->B(); 

我所希望做的就是重複使用相同的代碼在吐不同應用的大量,並且讓這個我可以「交換-out「並在特定情況下替換函數。

我使用PHP5.3(所以匿名函數應該工作,只是沒有在我使用他們的方式)。

非常感謝您的時間!

-GK

+0

您可以詳細瞭解您嘗試實施的這些不同的應用程序嗎?我在想,簡單的繼承可能是一個更好的解決方案,但更多的信息會有所幫助。 – 2010-06-13 22:02:15

+0

可能的重複:http://stackoverflow.com/questions/2938004/how-to-add-a-new-method-to-a-php-object-on-the-fly – 2010-06-13 22:15:52

+0

GK here, @Tim Cooper I我正在服務器端爲我正在開發的遊戲工作,服務器將由數十個應用程序組成,這些應用程序將管理遊戲的不同部分。他們都會非常相似,並且使用許多相同的類,但是他們都需要執行自定義函數的能力......摘要我知道,...感謝您的幫助! @ dev-null-dweller我認爲你的權利,我試着先查找這個問題,但顯然我沒有看夠硬,謝謝! – geekay 2010-06-14 01:00:59

回答

9

您可以使用__call魔術功能執行此任務。不是美女,但它的工作原理..

這樣的:

class A { 
    public $B; 

    public function __call($closure, $args) 
    { 
     call_user_func_array($this->$closure, $args); 
    } 
} 

$c = new A(); 

$c->B = function() { echo('HelloWorld'); }; 
$c->B(); 
+0

gk在這裏,我會研究這...我需要弄清楚是什麼...非常感謝我指出我在正確的方向!編輯 – geekay 2010-06-14 01:01:47

+0

以恢復downvote。我看到你發佈了與user358390完全相同的解決方案(減去一個小的差異),但是我沒有注意到時間如此接近,所以我給了疑問的好處 – Artefacto 2010-06-14 08:06:19

1

你可以做這些方針的東西(這也將與不是關閉回調工作):

<?php 
class A { 
    private $fun; 
    function setFun($fun) { 
     if (!is_callable($fun)) 
      throw new InvalidArgumentException(); 
     $this->fun = $fun; 
    } 
    public function fun() { 
     call_user_func_array($this->fun, func_get_args()); 
    } 
} 

$c = new A(); 

$c->setFun(function($a) { echo('HelloWorld ' . $a);}); 
$c->fun("here"); 

這給HelloWorld here

這就是說,你還應該考慮繼承或decorator pattern

4
# real ugly, but PoC... 

class a { 
    function __call($f, $x) { 
    call_user_func_array($this->$f, $x); 
    } 
} 

$a = new a; 
$a->b = function() { echo "Hello world"; }; 
$a->b(); 
4

FWIW:

PHP 5.3的治療的匿名函數是娛樂性。這是行不通的:

$c->B = function() { echo func_get_arg(0); }; 
$c->B("This fails :("); 

這將工作:

$c->B = function() { echo func_get_arg(0); }; 
$hilarious = $c->B; 
$hilarious("This works!"); 

要解決這個問題,你需要使用一個__call破解像一個provided by Oden

這種行爲可能變化的未來。該array dereferencing RFCrecently committed to PHP's trunk,以及補丁已經掀起了討論function call chaining,它的語法可能讓你想不__call黑客做什麼。不幸的是它是proven difficult in the past來獲得函數調用鏈接工作。

+1

僅僅使用熱鬧的方法有什麼問題? – mukunda 2014-09-30 00:05:00

+0

這不是*錯誤*,只是醜陋而黑客。 – Charles 2014-09-30 17:42:30

0

不是鉤住__call魔術方法到類,你可以而不是直接使用call_user_func執行調用。

class A { 
    public $b; 
} 

$c = new A(); 
$c->b = function(){echo('HelloWorld');}; 

call_user_func($c->b); // HelloWorld 

很顯然,PHP會提供一些語法來直接執行此操作。

1

這不再是PHP 7的問題;

// no error 
$result = ($this->anonFunc)(); 
$result = ($this->anonFunc)($arg1, $arg2, ...); 

查看更多有關AST