我有一个非常简单的OO类结构,无法理解为什么子类没有继承父类的属性和方法。
这是我设置的一个基本示例:
//Main class:
class Main{
//construct
public function Main(){
//get data from model
$data = $model->getData();
//Get the view
$view = new View();
//Init view
$view->init( $data );
//Get html
$view->getHTML();
}
}
//Parent View class
class View{
public $data, $img_cache;
public function init( $data ){
$this->data = $data;
$this->img_cache = new ImageCache();
}
public function getHTML(){
//At this point all data is intact (data, img_cache)
$view = new ChildView();
//After getting reference to child class all data is null
//I expected it to return a reference to the child class and be able to
//call the parent methods and properties using this object.
return $view->html();
}
}
//Child View Class
class ChildView{
public function html(){
//I get a fatal error here: calling img_cache on a non-object.
//But it should have inherited this from the parent class surely?
return '<img src="'.$this->img_cache->thumb($this->data['img-src']).'"/>';
}
}
所以我希望子类继承父类的属性和方法。然后,当我获得对子类的引用时,它应该能够使用img_cache
对象。但我在这里得到致命的错误:Call to a member function thumb() on a non-object
。
我在哪里出错了?
答案 0 :(得分:5)
您需要使用扩展基类http://php.net/manual/en/keyword.extends.php
来指定继承为您的孩子班试试这个
//Child View Class
class ChildView extends View{
public function html(){
//I get a fatal error here: calling img_cache on a non-object.
//But it should have inherited this from the parent class surely?
return '<img src="'.$this->img_cache->thumb($this->data['img-src']).'"/>';
}
}
同样,@ ferdynator说,你实例化的是父,而不是孩子,所以你的Main
类也需要更改为实例化ChildView
,而不是父View
//Main class:
class Main{
//construct
public function Main(){
//get data from model
$data = $model->getData();
//Get the view
$view = new ChildView();
//Init view
$view->init( $data );
//Get html
$view->getHTML();
}
}
答案 1 :(得分:0)
您不能通过实例化来创建子类。你把它变成了extends
超类。
然后你可以在抽象超类中创建一个抽象方法(或者如果你不希望它是抽象的那样,则创建一个默认实现),并通过声明在extends
超类的子类中实现它一个同名的方法。
//Main class:
class Main{
//construct
public function Main(){
//get data from model
$data = $model->getData();
//Get the view
$view = new ChildView(); // <--- changed
//Init view
$view->init( $data );
//Get html
$view->getHTML();
}
}
//Parent View class
abstract class View{ // <--- changed
public $data, $img_cache;
public function init( $data ){
$this->data = $data;
$this->img_cache = new ImageCache();
}
public abstract function getHTML(); // <--- changed
}
//Child View Class
class ChildView extends View{ // <--- changed
public function getHTML(){ // <--- changed
//I get a fatal error here: calling img_cache on a non-object.
//But it should have inherited this from the parent class surely?
return '<img src="'.$this->img_cache->thumb($this->data['img-src']).'"/>';
}
}
简单来说,子类和父类具有相同的实例。它们只包含来自不同类的代码,但它们仍然是同一个对象。只有同一个对象才能获得相同的属性。
BTW,使用__construct
作为构造函数(public function __construct
而不是public function Main
。使用类名作为构造函数名称是非常老式的,可能会被弃用(不确定)如果它已经是。)