【问题标题】:avoiding long class constants as parameters - PHP避免长类常量作为参数 - PHP
【发布时间】:2009-07-21 11:14:16
【问题描述】:

示例:

class Vendor_ClassName_Helper {
    CONST FIRST_OPTION  = 1;
    CONST SECOND_OPTION = 2;

    public function __construct($option, $otherArgument) {

    }
}

客户端代码:

$obj = new Vendor_ClassName_Helper(Vendor_ClassName_Helper::FIRST_OPTION, $var);

有什么避免排长队的好方法(这是一个相当短的例子)?也许其他方法可以实现相同?

【问题讨论】:

    标签: php oop coding-style


    【解决方案1】:

    我认为清晰比短代码更好。你可以试着想出不同的词来表达相同或不同的形式。对于您的示例,正​​如 Omega 指出的那样,它似乎并不算很糟糕,而且他在多行上拆分声明的方法也很好。

    这是另一个技巧:根据您的选项常量的作用,您可能希望使用工厂方法而不是 new-keyword。

    例如,

    class Example {
        private function __construct() { }
    
        public static method createA(..) { 
            //configure for mode A
            $cls = new self; 
            return $cls;
        }
    
        public static method createB(..) { 
            //configure for mode B
            $cls = new self; 
            return $cls;
        }
    }
    
    $x = Example::createA();
    

    【讨论】:

    • 你的意思是像建造者模式这样的东西? en.wikipedia.org/wiki/Builder_pattern
    • 不,只是一个工厂方法而不是构造函数。有时你可以这样命名方法,即使它通过调用 this 来传达你以这种方式配置的对象,它仍然比使用一些常量更短。
    【解决方案2】:

    我通过将参数分解成自己的块来避免长行并提高大多数语言的可读性...

    $obj = new Vendor_ClassName_Helper(
        Vendor_ClassName_Helper::FIRST_OPTION, 
        $var
    );
    

    但在我看来,两个选项并不总是值得的。遗憾的是,静态常量无法真正更改,您当然希望它们保持描述性。

    你在这里的东西还不错:)

    【讨论】:

      【解决方案3】:

      如果您将常量传递给构造函数,则建议您改为创建子类:

      class Vendor_ClassName_Helper {
        public function __construct($otherArgument) {
        }
      }
      
      class Vendor_ClassName_Helper_First extends Vendor_ClassName_Helper {
      }
      
      class Vendor_ClassName_Helper_Second extends Vendor_ClassName_Helper {
      }
      

      【讨论】:

      • 这种方法如何适合 Zend_Auth_Result 这样的类?
      • class Zend_Auth_Result_Success extends Zend_Auth_Result {} 等。我想。
      • 这是一个很好的答案。但是我在想(并且没有写过)客户端代码有一个类 Zend_Auth_Result_Success 是相当尴尬的,然后逐个案例询问是否例如 $result->getCode() === Zend_Auth_Result::FAILURE_IDENTITY_NOT_FOUND。 __construct() 的长常量名称已经消失,但现在您必须引用另一个类的常量而不是您获得的类的常量(如果它是接口常量则不同)。
      • 这表明您的代码存在另一个问题。您应该用多态性替换条件。见:refactoring.com/catalog/replaceConditionalWithPolymorphism.html
      • 这是有条件的客户端代码,就像在 ZF 手册中一样:framework.zend.com/manual/en/…
      【解决方案4】:

      不为类或常量的名称使用较短的名称​​(并且使您的代码无法理解,这是您绝对不想要的),不,我认为没有办法-- 至少,不是 PHP

      PHP 5.3 为 PHP 添加命名空间;有了这些,您可能会得到更短/更好的东西;但这意味着使用 PHP 5.3,这不是很多托管公司提出的(5.3.0 是在今年 6 月底发布的,因此可能需要一段时间才能在任何地方使用......)

      关于 PHP 中的命名空间的更多信息(仅引用几个链接)

      【讨论】:

        【解决方案5】:

        我认为没有更好的方法(没有动态的方法):

        class LongClassName
        {
            const B = 3;
        }
        
        class LCN
        {
            const B = LongClassName::B;
        }
        
        echo LCN::B;
        

        【讨论】:

          猜你喜欢
          • 1970-01-01
          • 2019-06-19
          • 1970-01-01
          • 1970-01-01
          • 2021-12-08
          • 1970-01-01
          • 2011-06-12
          • 1970-01-01
          • 2016-01-06
          相关资源
          最近更新 更多