Passing an instance method as argument in PHP

28,980

Solution 1

  • Before PHP 5.4, there was no type named callable, so if you use it as a type hint, it means "the class named callable". If you use PHP >= 5.4, callable is a valid hint.

  • A callable is specified by a string describing the name of the callable (a function name or a class method name for example) or an array where the first element is an instance of an object and the second element is the name of the method to be called.

For PHP < 5.4, replace

public function add(callable $function)

with:

public function add($function)

Call it with:

$listener->add(array($this, 'bar'));

Solution 2

Methods and properties have separate namespaces in PHP, which is why $this->bar evaluates to null: You're accessing an undefined property.

The correct way to create an array in the form of array($object, "methodName"):

Passing the callback correctly:

$listener->add(array($this, 'bar'));  

The type hint you have given is okay—as of PHP 5.4, that is.

Solution 3

I don't think you can specify a callable this way...

Try

$listener->add(array($this, 'bar'));

And see http://php.net/manual/en/language.types.callable.php too.

Share:
28,980
Gergely Fehérvári
Author by

Gergely Fehérvári

Updated on November 25, 2020

Comments

  • Gergely Fehérvári
    Gergely Fehérvári over 3 years

    I would like to create a Listener class

    class Listener {
        var $listeners = array();
        
        public function add(callable $function) {
            $this->listeners[] = $function;
        }
    
        public function fire() {
            foreach($this->listeners as $function) {
                call_user_func($function);
            }
        }
    }
    
    class Foo {
        public function __construct($listener) {
            $listener->add($this->bar);
        }
        
        public function bar() {
            echo 'bar';
        }
    }
    
    
    
    $listener = new Listener();
    $foo = new Foo($listener);
    

    But this code fails with this error:

    Notice: Undefined property: Foo::$bar in index.php on line 18

    Catchable fatal error: Argument 1 passed to Listener::add() must be callable, null given, called in index.php on line 18 and defined index.php on line 5

    What am I doing wrong?

  • phant0m
    phant0m over 11 years
    You don't need a reference.
  • rid
    rid over 11 years
    ... because objects are always treated as references and never copied.