update page now

Voting

: zero plus four?
(Example: nine)

The Note You're Voting On

kdelux at gmail dot com
15 years ago
Here is an example of one way to define, then use the variable ( $this ) in Closure functions.  The code below explores all uses, and shows restrictions.

The most useful tool in this snippet is the requesting_class() function that will tell you which class is responsible for executing the current Closure().  

Overview:
-----------------------
Successfully find calling object reference.
Successfully call $this(__invoke);
Successfully reference $$this->name;
Successfully call call_user_func(array($this, 'method'))

Failure: reference anything through $this->
Failure: $this->name = ''; 
Failure: $this->delfect(); 

<?php
 
    
    
    function requesting_class()
    {
        foreach(debug_backtrace(true) as $stack){
            if(isset($stack['object'])){
                return $stack['object'];
            }
        }
        
    }
    
        
    
    
    
    
    class Person
    {
        public $name = '';
        public $head = true;
        public $feet = true;
        public $deflected = false;
        
        function __invoke($p){ return $this->$p; }
        function __toString(){ return 'this'; } // test for reference
        
        function __construct($name){ $this->name = $name; }
        function deflect(){ $this->deflected = true; }
        
        public function shoot()
        { // If customAttack is defined, use that as the shoot resut.  Otherwise shoot feet
            if(is_callable($this->customAttack)){
                return call_user_func($this->customAttack);
            }
            
            $this->feet = false;
        }
    }

    $p = new Person('Bob');

    
    $p->customAttack = 
                function(){
                    
                    echo $this; // Notice: Undefined variable: this
                    
                    #$this = new Class() // FATAL ERROR
                    
                    // Trick to assign the variable '$this'
                    extract(array('this' => requesting_class())); // Determine what class is responsible for making the call to Closure
                    
                    var_dump( $this  );  // Passive reference works
                    var_dump( $$this ); // Added to class:  function __toString(){ return 'this'; }
                    
                    $name = $this('name'); // Success
                    echo $name;            // Outputs: Bob
                    echo '<br />';
                    echo $$this->name;
                    
                    call_user_func_array(array($this, 'deflect'), array()); // SUCCESSFULLY CALLED
                    
                    #$this->head = 0; //** FATAL ERROR: Using $this when not in object context
                    $$this->head = 0;  // Successfully sets value
                    
                };
 
    print_r($p);
    
    $p->shoot();
    
    print_r($p);

    
    die();

?>

<< Back to user notes page

To Top