2

Within my code, I have two classes- the first "Foo" initiates the second "Bar"... what I want to do is find some method of using the functions and variables from the parent.

class Bar {
    function __construct() {
        /* 
         * From within this function, how do I access either the returnName() function
         * OR the $this -> name variable from the class above this?
         * The result being:
         */
        $this -> name = parent::returnName();
        $this -> else = parent -> name;
    }
}

class Foo {
    function __construct() {
        $this -> name = 'Fred';
        $this -> var = new Bar();
    }

    function returnName() {
        return $this -> name;
    }
}

$salad = new Foo();

I realise the syntax of "parent" refers to either an implement or extends, but is it possible to use this kind of method?

lukesrw
  • 1,692
  • 1
  • 14
  • 20

2 Answers2

3

You can inject $this (the Foo class) in the constructor of Bar

<?php
class Bar {
    function __construct($fooClass) {
        /* 
         * From within this function, how do I access either the returnName() function
         * OR the $this -> name variable from the class above this?
         * The result being:
         */
        $this -> name = $fooClass->returnName();
        $this -> else = $fooClass -> name;
    }
}

class Foo {
    function __construct() {
        $this -> name = 'Fred';
        $this -> var = new Bar($this);
    }

    function returnName() {
        return $this -> name;
    }
}

$salad = new Foo();
Daan
  • 12,099
  • 6
  • 34
  • 51
  • Thanks, I knew I would do this- though I didn't want to pass as an argument unless I absolutely had to. – lukesrw Mar 17 '16 at 12:55
  • [debug_backtrace()](http://php.net/manual/en/function.debug-backtrace.php) Take a look at my answer for an example with your classes ;) – Tanuel Mategi Mar 17 '16 at 13:00
  • For Daan, the Bar class is now trying to use a function from Foo, "Call to undefined method Bar::returnName()". Solution to this? – lukesrw Mar 17 '16 at 13:04
  • You're calling `returnName()` statically (`::`). Call it like this `$fooClass->returnName();` – Daan Mar 17 '16 at 13:07
  • I'm not using ::, I am using $this -> returnName(); How would I ensure that it always uses Foo class, no matter whether it is called by Foo OR Bar. – lukesrw Mar 17 '16 at 13:10
  • Realised the problem, the function was being called as static in one place, which triggered the dynamic one. – lukesrw Mar 17 '16 at 13:22
0

Handle with care

This is not a 100% clean solution, but will work. Your code should be well documented to avoid future confusion.

There is a very cool function called debug_backtrace()

It gives you information about all the calls that were made to get to this function, including the filename, the line it was called, the called function, the class and object name and the arguments.

Here is how you could use it:

class Bar {
    function __construct() {

        //get backtrace info
        $trace = debug_backtrace();
        //get the object from the function that called class
        //and call the returnName() function
        $this->name = $trace[1]['object']->returnName();
        echo $this->name;

        //want more info about backtrace? use print_r($trace);
    }
}

class Foo {
    function __construct() {
        $this -> name = 'Fred';
        $this -> var = new Bar();
    }

    function returnName() {
        return $this -> name;
    }
}

$salad = new Foo();

Result:

Fred

Tanuel Mategi
  • 1,253
  • 6
  • 13
  • The function part of my question is currently the most important answer, though this seems like it might be best for variables- am I right in thinking this would be slower than using $this as an argument when calling Bar? – lukesrw Mar 17 '16 at 13:05
  • You can try a benchmark, but it works pretty fast. I use debug_backtrace() in a few of my applications and the whole page doesnt take more than 0.08 seconds to load. edit: also take a look here: [PHP debug_backtrace in production code to get information about calling method?](http://stackoverflow.com/a/347014/3338286) – Tanuel Mategi Mar 17 '16 at 13:07
  • Thanks! Still looking into getting functions to work, I'll be sure to use this if needed. – lukesrw Mar 17 '16 at 13:11