Warning: file_get_contents(/data/phpspider/zhask/data//catemap/1/php/288.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

Warning: file_get_contents(/data/phpspider/zhask/data//catemap/4/oop/2.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_Optimization - Fatal编程技术网

包装/重用/克隆PHP对象(代码优化)

包装/重用/克隆PHP对象(代码优化),php,oop,optimization,Php,Oop,Optimization,设想两个类共享几乎相同的方法和属性,它们都扩展了父类,但差异很小 class fields { public function __construct() { global $id; $this->id = $id++; } } class input extends fields { public function __construct() { parent::__construct(); } public function draw() { echo '

设想两个类共享几乎相同的方法和属性,它们都扩展了父类,但差异很小

class fields { 
 public function __construct() {
  global $id;
  $this->id = $id++;
 }
}

class input extends fields {
 public function __construct() {
  parent::__construct();
 }
 public function draw() {
  echo '<input>';
 }
}

class textarea extends fields {
 public function __construct() {
  parent::__construct();
 }
 public function draw() {
  echo '<textarea>';
 }
}
我刚刚复制了整个类并修改了几行,但我觉得这是浪费

最终答案 多亏了这些人,以下是电话示例的综合答案:

abstract class fields { 
 private static $masterid = 0;
 public function __construct() {
  $this->id = self::$masterid++;
 }
}

class input extends fields {
 public $data;
 public function __construct($new = '') {
  parent::__construct();
  if ($new) $this->data = $new;
  else $this->data = 'Hello';
 }
 public function draw() {
  echo '<input>'.$this->export().'</input>';
 }
 public function export() {
  return 'ID '.$this->id.' = '.$this->data;
 }
}

class textarea extends input {
 public function __construct($new = '') {
  parent::__construct($new);
 }
 public function draw() {
  echo '<textarea>'.$this->export().'</textarea>';
 }
}

$a = new textarea();
$a->draw();
$a = new textarea('World');
$a->draw();
$a = new input('!');
$a->draw();

//Outputs:
// <textarea>ID 0 = Hello</textarea>
// <textarea>ID 1 = World</textarea>
// <input>ID 2 = !</input>
抽象类字段{
私有静态$masterid=0;
公共函数构造(){
$this->id=self::$masterid++;
}
}
类输入扩展字段{
公共数据;
公共函数构造($new=''){
父项::_构造();
如果($new)$this->data=$new;
else$this->data='Hello';
}
公共职能部门{
回显“”。$this->export();
}
公共功能导出(){
返回'ID'。$this->ID.='。$this->data;
}
}
类textarea扩展输入{
公共函数构造($new=''){
父项::u构造($new);
}
公共职能部门{
回显“”。$this->export();
}
}
$a=新文本区域();
$a->draw();
$a=新文本区域(“世界”);
$a->draw();
$a=新输入(“!”);
$a->draw();
//产出:
//ID0=你好
//ID 1=世界
//ID2=!
使“fields”类具有绘制方法:

public function draw($msg) {
    echo $msg;
}
然后在textarea或input类中输入:

parent::draw("<input>");
然后在子类中:

parent::__construct(1); //Or whatever ID you want
按照您的方式,ID在每次设置时都是相同的值,这将导致字段的每个子类都具有相同的ID。这样,每个子类都将具有单独的ID

也因为我很好,这里是所有的组合:

public class field {
    $id;
    public __construct($id) {
        $this->id = $id;
    }

    public function draw($msg) {
        echo $msg;
    }
}

public class input extends field {
    public __construct() {
        parent::__construct(1);
        parent::draw("<input>");
    }
}

public class textarea extends field {
    public __construct() {
        parent::__construct(2);
        parent::draw("<textarea>");
    }
}
公共类字段{
$id;
公共构造($id){
$this->id=$id;
}
公共职能部门抽签($msg){
echo$msg;
}
}
公共类输入扩展字段{
公共构造(){
父项::_构造(1);
父::draw(“”);
}
}
公共类textarea扩展字段{
公共构造(){
父项::_u构造(2);
父::draw(“”);
}
}

这就是我根据你所说的把它组合起来的方法。不过我可能弄错了你的要求。你能从中看出我主要是一个Java程序员吗?

让fields类成为一个抽象类,就像Darren建议的那样,让“draw”方法成为fields类的函数

现在有一个技巧,您希望输入类扩展字段,但重写draw方法。这将允许您自定义该方法的功能,并且您仍然可以从其中调用父变体


最后,由于textarea类与input类有许多相似之处,所以让textarea扩展input。从而继承了字段和输入的属性和方法。

不清楚您想要做什么。对于您给出的示例,我认为结构是可以的,但是您应该做一些更改,特别是对于构造函数。我认为构造函数应该是抽象的,带有一个抽象方法draw()

抽象类字段{
//使用静态成员跟踪id,而不是将其设置为全局
私有静态$id=0;
//使用实例变量跟踪特定实例的id
私人$myId;
公共函数构造(){
//增加静态ID并将其分配给实例ID。
$this->myId=self::$id++;
}
//提供公共getter,以便无法更改ID
//在这个班级之外
公共函数getId(){
返回$this->myId;
}
public abstract draw();//确保所有子类都实现draw()方法。
}
类输入扩展字段{
//如果不添加任何内容,则不需要调用父构造函数
//否则,它将被自动调用。
公共职能部门{
回声';
}
}
类textarea扩展字段{
公共职能部门{
回声';
}
}

您不能为$this引用赋值。。可悲的lol。无论如何,你能描述一下如何使用它吗?这是一个非常简单的主题表单生成器版本。我不想优化上面的代码,因为它具有代表性,不应该被考虑。我试图描述一下我想要完成的目标的概念。基本上,包装一个对象,并且仍然可以使用它来调用公共方法和访问公共属性。我想把它抽象化是正确的方法,但是如果你只是想回显一些我不想的东西,那是必要的,但是这个脚本就像那样毫无意义,所以我想会有一种比我列出的更复杂的绘图方法。我从来没有做过PHP,你注意到我的语法中有任何错误吗?好吧,这取决于他在为我能猜到的将用于呈现UI组件的内容构建库方面会走多远。如果他打算把它复杂化,多层继承将对他有所帮助。关于你的语法,我确实注意到缺少了一个分号,虽然它不会对脚本产生负面影响,但是类属性应该有访问修饰符,构造函数通常不需要声明为公共的,只是需要更好的实践。我想这就是答案(最后一段),只要让textarea根据需要扩展输入和重载即可。用我更复杂的代码来尝试这一点。正确,我应该说方法重写。很抱歉,我删除了那个注释,因为php中实际上有一个重载系统,只是与其他语言不同,尽管这个答案不能确保id是唯一的。此外,还可以从每个子构造函数调用父::draw()。我不认为这是故意的行为,是谁投票赞成的?它不起作用,它引入了神奇的数字,这很糟糕!对不起,我对PHP非常生疏,大概一年都没做过。我现在太习惯Java了。谢谢你的回复。在实际代码中,fields类确实有一个draw类,但它是重载的,并根据需要在子类中通过parent::draw调用。我不想优化上面的代码,我只是想描述一下我想要实现的概念
public $id
public function __construct($id) {
    $this->id = $id;
}
parent::__construct(1); //Or whatever ID you want
public class field {
    $id;
    public __construct($id) {
        $this->id = $id;
    }

    public function draw($msg) {
        echo $msg;
    }
}

public class input extends field {
    public __construct() {
        parent::__construct(1);
        parent::draw("<input>");
    }
}

public class textarea extends field {
    public __construct() {
        parent::__construct(2);
        parent::draw("<textarea>");
    }
}
abstract class fields { 

   // Use a static member to keep track of id's instead of making it global
   private static $id = 0;

   // Use an instance variable to keep track of a particular instance's id
   private $myId;

   public function __construct() {
      // Increment the static ID & assign it to the instance id.
      $this->myId = self::$id++;
   }

   // Provide a public getter, so that the ID can't be changed
   // externally to this class
   public function getId() {
       return $this->myId;
   }

   public abstract draw(); // Make sure all sub classes implement a draw() method.

}

class input extends fields {
   // Don't need to call the parent constructor if you're not adding anything
   // else. It will be called automatically.

   public function draw() {
      echo '<input>';
   }
}

class textarea extends fields {
   public function draw() {
      echo '<textarea>';
   }
}