Warning: file_get_contents(/data/phpspider/zhask/data//catemap/1/php/292.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Php 两个类使用的修改方法_Php_Oop - Fatal编程技术网

Php 两个类使用的修改方法

Php 两个类使用的修改方法,php,oop,Php,Oop,我有两个类,它们有几乎相同的方法,都称为myMethod(),然而,myChild2::myMethod()中有一行额外的代码,它使用了一个局部变量。我宁愿不要在两个子类中重复代码。我想我可以将myMethod移动到myParent,然后添加一个if语句来检测哪个子类正在调用该方法,但我猜这是不对的。最干净的方法是什么?多谢各位 class myParent { //code... } class myChild1 extends myParent { public funct

我有两个类,它们有几乎相同的方法,都称为myMethod(),然而,myChild2::myMethod()中有一行额外的代码,它使用了一个局部变量。我宁愿不要在两个子类中重复代码。我想我可以将myMethod移动到myParent,然后添加一个if语句来检测哪个子类正在调用该方法,但我猜这是不对的。最干净的方法是什么?多谢各位

class myParent
{
    //code...
}

class myChild1 extends myParent
{
    public function myMethod()
    {
        // A bunch of code common to both myChild1::myMethod() and myChild2::myMethod() goes here
        // A bunch more code common to both myChild1::myMethod() and myChild2::myMethod() goes here
    }
}

class myChild2 extends myParent
{
    public function myMethod()
    {
        // A bunch of code common to both myChild1::myMethod() and myChild2::myMethod() goes here
        someOtherLineOfCode($someLocalVariable); // A single unique line of code goes here which uses a local variable
        // A bunch more code common to both myChild1::myMethod() and myChild2::myMethod() goes here
    }
}

你可以这样做:

class myParent
{
    public function myMethod()
    {
        // A bunch of code common to both myChild1::myMethod() and myChild2::myMethod()     goes here
        $this->templateMethod($someLocalVariable);
        // A bunch more code common to both myChild1::myMethod() and     myChild2::myMethod() goes here
    }

    protected function templateMethod($x) {}
}


class myChild2 extends myParent
{
    protected function templateMethod($x) {
        // some extra line
    }
}

取决于你到底在做什么,我认为这是一个干净的解决方案

我想把它移到
myParent
并添加一个构造函数参数。取决于什么是
someOtherLineOfCode
,但您至少可以添加一个标志来确定是否执行它,如下所示:

class myParent
{
    public function __construct($shouldExecute) {
        $this->$executeSomeOtherCode = $shouldExecute;
    }

    public function myMethod()
    {
        // A bunch of code common to both myChild1::myMethod() and myChild2::myMethod() goes here

        if($this->$executeSomeOtherCode) {
            someOtherLineOfCode($someLocalVariable); // A single unique line of code goes here which uses a local variable
        }

        // A bunch more code common to both myChild1::myMethod() and myChild2::myMethod() goes here
    }

    //code...
}

class myChild1 extends myParent
{
    public function __construct()(
        parent::__construct(FALSE);
        // Do stuff specific for Bar
    }

    // Other code
}

class myChild2 extends myParent
{
    public function __construct()(
        parent::__construct(TRUE);
        // Do stuff specific for Bar
    }

    // Other code
}

有几个选项可以实现你的目标。选择哪一个取决于独特线路的用途

覆盖该方法

首先,您可以在父级中
myMethod()
,然后在myChild2()中重写它,包括额外的行,然后调用父级。如果额外的代码行可以独立于
myMethod()
的其余部分执行,则这将起作用:

传递标志参数

如果执行顺序很重要,您可以在运行时检测到对额外功能的需求:

class Parent
{
     function myMethod($enableExtraFunctionality=false)
     {
          // Common stuff
          if ($enableExtraFunctionality) 
          {
               someOtherLineOfCode($someLocalVariable);
          }
          // More common stuff
      }
 }
然后仅在
myChild2()
中将变量设置为true:

如果愿意,还可以将该标志作为类变量而不是函数参数传递

检测调用类的名称


作为前一种方法的变体,您可以检测子类的名称。有关详细信息,请查看中的评论。

谢谢。看起来没有完全干净的解决方案。作为第四个选项,请参见schlimpf的建议。方法1将不起作用(对于我的应用程序),因为它无法独立于myMethod()的其余部分执行。您是否建议传递标志或检测类名?检测调用类名将需要更少的代码行,因为您不必重写
myMethod()
,而是使父级依赖于特定命名子级的存在。如果这是我的代码,我被迫在两者之间做出选择,我会选择标志选项。我同意,并将使用标志选项。你认为我应该把国旗作为孩子的私有财产吗?我不认为我会把它当作财产。它只会被使用一次,并且值总是为真的。myChild2::myMethod()函数中的注释应该足够了。我也想过这样做,但不确定它是否更直观,就像IF语句一样。这难道不需要对实例变量进行显式的
myChild::templateMethod()
调用吗?按原样,
myParent::myMethod()
将执行对
templateMethod()
的调用,而不填充
$someLocalVariable
。这种方法很新颖,但可能比我理想的方法复杂一点。
class Parent
{
     function myMethod($enableExtraFunctionality=false)
     {
          // Common stuff
          if ($enableExtraFunctionality) 
          {
               someOtherLineOfCode($someLocalVariable);
          }
          // More common stuff
      }
 }
 class myChild2 extends Parent
 {
     function myMethod()
     {
          parent::myMethod(true);
     }
  }