Instantiating classes and accessing methods from different classes
I'm trying to use a Class_B function in one of Class_A's functions. But a lot of Class_B's functions include $this
which causes problems. These are both classes (each class is of course in its own file):
class Class_A
{
function hello()
{
require('class_b.php');
echo 'Hello ' . Class_B::person();
}
function bye()
{
require('class_b.php');
echo 'Bye ' . Class_B::person();
}
}
class Class_B
{
function person()
{
// various operations and variables
echo $this->get_user($id);
}
}
When I run the Class_A file I get Call to undefined method Class_A::person() in (...)
because I think the $this value is changed when I instantiate the Class_A class. It overrules the Class_B value. How can I stop this?
Also, another question: how can I access Class_B from every function in Class_A? I don't want to redeclare the class. Do I need to do this:
class Class_A
{
开发者_如何学运维 function function1()
{
require('class_b.php');
$class_b = new Class_B();
// code
}
function function2()
{
require('class_b.php');
$class_b = new Class_B();
// code
}
}
Or do I need to use a constructor or something?
By Class_B::person()
you are calling the method statically. So you should declare the person()
method as static and can't use $this
because you don't have an instance of Class_B
.
If you need an instance of Class_B
, just create it and store in the class_B
on construction.
class Class_A {
private $b;
function __construct()
{
$this->b = new Class_B();
}
function stuff()
{
$this->b->person();
}
Don't put require
inside a method. Code in an include
d file inherits the scope of the place where you include it, and in your example, bad things happen. Also, for class definition scripts, consider require_once
instead of require
, to avoid multiple definitions.
As a rule of thumb, put all include
s and require
s at the top of your script. Better yet, set up a class autoloader, and register it in an auto_prepend
script. That way, you won't have to manually include anything at all (at least not for class definitions).
What you might want is dependency injection, whereby you pass an object of Class_B
into Class_A
's constructor and hold it as a property in Class_A
. It then becomes available in Class_A
as $this->classB
or similar.
// Include Class_B code outside the class.
require_once('class_b.php');
class Class_A {
// Property to hold Class_B
public $b;
// Constructor
public function __construct($b) {
$this->b = $b;
}
public function function1(){
// code
$this->b;
}
public function function2(){
// code
$this->b;
}
}
// Now call your objects:
// The Class_B which will be injected into A
$b = new Class_B();
// Your Class_A, which holds an instance of Class_B as a property
$a = new A($b);
精彩评论