【问题标题】:Confused about abstract class in php对php中的抽象类感到困惑
【发布时间】:2012-11-18 18:51:40
【问题描述】:

如果我有这样的抽象类:

abstract class MyApp
{

   public function init()
   {
      $this->stuff = $this->getStuff();

   }
   public function getStuff()
   {
      return new BlueStuff();
   }
}

然后我有一个从这个抽象类扩展而来的类,如下所示:

class MyExtendedClass extends MyApp
{
   public function init()
   {
      parent::init();
   }

   public function getStuff()
   {
      return new RedStuff();
   }
}

如果我这样做:

$myobj = new MyExtendedClass();
$myobj->init();

为什么会调用子类的 getStuff 方法? $this 不是在抽象类的上下文中吗?如果是这样,抽象类的方法不应该被调用吗?

谢谢!

【问题讨论】:

  • 你试过了吗?你得到了什么? (除了语法无效的错误吗?)

标签: php abstract


【解决方案1】:

新答案

在 PHP 中,您可以使用子类,就好像父类中不存在于子类中的所有方法都已复制到子类中一样。因此,您的示例将与以下内容相同:

class MyExtendedClass extends MyApp {
    public function init() {
        $this->stuff = $this->getStuff();
    }

    public function getStuff() {
        return new RedStuff();
    }
}

只要把子类想象成拥有父类的所有代码,你通常就可以了。此规则有一个例外:属性。一个类的private 属性只能被该类访问,子类不能访问父类的private 属性。为此,您需要将 private 属性更改为 protected 属性。


原答案

PHP 中的Abstract classes 就像普通类一样,但有一个很大的不同:它们不能被启动。这意味着你不能做new AbstractClass();

由于它们的工作方式与其他所有方面的常规课程完全相同,因此 extending classes 也是如此。这意味着 PHP 会首先尝试在启动的类中查找方法,如果抽象类不存在,则只在抽象类中查找。

因此,在您的示例中,这意味着调用了来自 MyExtendedClassgetStuff() 方法。此外,这意味着您可以省略 MyExtendedClass 中的 init() 方法。

【讨论】:

  • 感谢您的回答。我担心的是,一旦调用了 parent::init,上下文就会改变,所以 $this 就变成了 Abstract 的上下文,对吧?那为什么,当做 $this->getStuff();子方法被调用?如果我在抽象类的上下文中。
  • 我已经编辑了我的问题,所以它实际上符合我的疑问。谢谢!
  • @HommerSmith:我已经编辑了我的答案以反映您更改的问题。希望这可以解决问题。
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2019-09-07
  • 2012-03-22
  • 2020-04-19
  • 1970-01-01
  • 1970-01-01
  • 2011-07-05
相关资源
最近更新 更多