PHP不止一个构造函数

时间:2012-04-29 10:15:54

标签: php oop encapsulation

我正在从网站上学习PHP。我对其他语言有一些OOP背景。
问题1:
这是使用2个不同的参数集在PHP中实现构造函数的正确方法吗?
问题2:
当我在PHP中使用__set magic方法时,我希望此类中的comment_id不能从__set函数更改。这可能在PHP中完成吗?

 class Comment{
    private $comment_id;
    private $image_id;
    private $author_id;
    private $comment_text;
    private $created_at;

    public function __construct()
    {
        $arguments = func_get_args();
        $num = sizeof($arguments)
        switch($num)
        {
            case 0;
                break;
            case 3:
                this->image_id = $arguments[0];
                this->author_id = $arguments[1];
                this->comment_text = $argument[2];
                break;
            case 5:
                this->comment_id = $arguments[0];
                this->image_id = $arguments[1];
                this->author_id = $argument[2];
                this->comment_text = $argument[3];
                this->created_at = $argument[4];
                break;
            default:
                break;

        }
    }

    public function __get($property)
    {
        if(property_exists($this,$property))
        {
            return $this->$property;
        }
    }

    public function __set($property_name,$value)
    {
        if(property_exists($this,$property_name))
        {
            $this->$property_name = $value; 
        }

    }
    }

4 个答案:

答案 0 :(得分:2)

  1. 在PHP中声明“多个”构造函数的方法有很多,但它们都不是“正确”的方法(因为PHP技术上不允许这样做)。但是,我没有看到你在那里做的有什么不妥。如果您想了解更多信息,请查看this Stack Overflow question

  2. 您可以使用if语句。也许是这样的事情?

    public function __set($property_name,$value)
    {
        $hidden_properties = array(
            'comment_id',
            'any_other_properties'
        );
    
        if(!in_array($property_name, $hidden_properties) &&
           property_exists($this, $property_name))
        {
            $this->$property_name = $value; 
        }
    }
    

答案 1 :(得分:1)

正如此处和Best way to do multiple constructors in PHP所示,有很多方法可以在PHP中声明multiple构造函数。 这是另一个例子:

<?php

class myClass {
    public function __construct() {
        $get_arguments       = func_get_args();
        $number_of_arguments = func_num_args();

        if (method_exists($this, $method_name = '__construct'.$number_of_arguments)) {
            call_user_func_array(array($this, $method_name), $get_arguments);
        }
    }

    public function __construct1($argument1) {
        echo 'constructor with 1 parameter ' . $argument1 . "\n";
    }

    public function __construct2($argument1, $argument2) {
        echo 'constructor with 2 parameter ' . $argument1 . ' ' . $argument2 . "\n";
    }

    public function __construct3($argument1, $argument2, $argument3) {
        echo 'constructor with 3 parameter ' . $argument1 . ' ' . $argument2 . ' ' . $argument3 . "\n";
    }
}

$object1 = new myClass('BUET');
$object2 = new myClass('BUET', 'is');
$object3 = new myClass('BUET', 'is', 'Best.');

来源:the easiest way to use and understand multiple constructors:

希望这有帮助。

答案 2 :(得分:0)

对于问题1,请查看此帖Best way to do multiple constructors in PHP

对于问题2,您可以过滤掉__set函数中的comment_id属性。

public function __set($property_name,$value)
{
    if (property_exists($this, $property_name) && $property_name !== 'comment_id')
    {
        $this->$property_name = $value; 
    }

}

答案 3 :(得分:0)

  

问题1

     

这是使用2组不同参数在PHP中实现构造函数的正确方法吗?

是的(好吧,至少 正确的方式,正如其他海报指出的那样)。我能想到的一个改进是在default分支中抛出异常。

  

问题2

     

当我在PHP中使用__set magic方法时,我希望无法从__set函数更改此类中的comment_id。这可能在PHP中完成吗?

当然,你几乎就在那里:

public function __set($property_name,$value) {
  if(property_exists($this,$property_name)) {
    if($property_name == "comment_id") {
      // throw an exception? ignore?
    } else {
      $this->$property_name = $value;
    }
  } else {
    throw new Exception(strtr("Class {class} does not have property {property}!", array(
      '{class}' => get_class($this),
      '{property}' => $property_name,
    ));
  }
}

但这里有一个限制,请参阅this comment