2013-12-13 40 views
1

直接在__construct中设置属性是不好的做法。这些代码块之一是否更适合面向对象的PHP?直接在__construct中设置属性是不好的做法吗?

我知道这是不好的做法,这样做的类外...

class person { 
    protected $name; 

    function __construct($persons_name) { 
     $this->set_name($persons_name); 
    } 
    function set_name($new_name){ 
     $this->name = $new_name; 
    } 
} 

VS.

class person { 
    protected $name; 

    function __construct($persons_name) { 
     $this->name = $persons_name; 
    } 
    function set_name($new_name){ 
     $this->name = $new_name; 
    } 
} 
+0

无论如何,我认为''set_name()'是不好的练习,因为你应该使用'__set()'。其他人则认为,获得者和制定者都是不好的练习。拿你的选择。 – 2013-12-13 19:49:03

+0

有没有什么好书可以学习正确的PHP OOP方法? –

+2

'set_name()'在这里是多余的,因为你的属性是公共的。为什么有人要用一种方法来改变它呢?让它保护或私人只是这样你可以有一个理由使用该方法也不是一个好主意。安装程序适用于有充分理由直接无法访问的属性 –

回答

1

这两个陈述基本上都可以。有一点点区别你应该注意:

  • set_name()方法是可覆盖的。这意味着扩展该方法的函数可以改变它的行为。这也不好或坏,你应该考虑是否期望你的应用程序做到这一点。

  • 正如hek2mgl所述,您还可以使用该方法执行其他任务来验证构造函数生成的数据并避免重复的代码。

  • 其次是表现。虽然你永远不应该将性能作为优先级进行编码(总是首先要清理可读的代码),但使用方法会使服务器花费几个CPU周期,这在其他地方可能很有用。

如果你希望你的应用程序使用的set_name()方法,并使其“针对重载安全”您可以使用final关键字。

0

尽管在这个例子中它没有区别,第二个是“更好”。这是因为通常你会在setter方法中包含一些验证检查或类似的东西。所以,直接设置属性时,你会绕过它们。

思考面向对象的设计时,另一个重要一点是,如果您呼叫的二传手,为您提供分等级的可能性,改变的过程,而不需要覆盖整个构造

+0

这可能会导致在模型中包含业务逻辑。大多数情况下,制片人只是一个制片人。 – Jessica

+0

@ hek2mgl您的意思是第一个更好,因为'_ persons“设置了'_ persons_name'时,它可以像setter一样验证它吗? –

+0

是的,如果有一些验证,或者计划在setter中运行的类型检查,为什么绕过它们?如果制定者真的只设置了价值,没有任何进一步的检查,那么你可以使用公共财产 – hek2mgl

1

它不是”事实被认为是不好的做法;它实际上只取决于set_name($name)实际上在做什么。

如果您只是直接从参数设置变量的值(例如在您的问题中),那么会出现额外函数调用的性能成本。这将是一个非常小的。

但是,如果您在编辑/修改参数前设置了参数,那么最好将函数封装在方法中以避免代码重复。

+1

在OP的问题中不使用setter方法的原因实际上与性能没有任何关系(我们在这里说的是微秒) - 它有有明智的,可读的代码。如果你已经拥有了属性的新值,那么你不应该使用setter方法来更新公共属性......为什么当'$ this-> property = $ value;'有效时编写一个方法?我能想到的唯一警告是,如果你怀疑某处可能会使该属性变为私有,或者将来可能会改变属性设置过程以涉及更复杂的逻辑。 –

+0

@BenD我对性能的评论并不意味着推断这是不使用setter的主要原因;只需要考虑一点,因此“非常小”。我同意*取决于正在修改的内容,包含的财产的可见性。 – AlexP

0

我认为,它主要归结为个人喜好。但是,有些值不能直接设置给变量,比如新的类实例,必须在构造函数中赋值。

相关问题