代码之家  ›  专栏  ›  技术社区  ›  ADJenks

引用实例化对象方法的更好方法是什么?

  •  1
  • ADJenks  · 技术社区  · 10 年前

    好的,我已经创建了一个简单的重现我遇到的问题,我已经测试了代码并运行了。我的问题是, 如何调用Paper->important()来自岩石内部->mb(),当一个rock实例位于一个paper实例内而没有将实例化对象注入到每个方法中时? 我通过将我的论文中的$this传递/注入rock方法来实现这一点。主要问题是,只有一种岩石方法需要它,所以我如何才能轻松 访问实例化对象的方法,而不将它们传递给每个函数 考虑到我正在运行许多功能?最后一个问题是,也许 这有关系吗 我把它们注射到每一种方法中, 它需要额外的内存吗 或资源? 我应该通过引用传递$this吗? ,它会节省内存吗?此外,当我传递未使用的额外参数时会发生什么?

    <?php
    class Rock{
        public function ma($args){ //what happens when it gets injected into this function?
            return $args." in ma";
        }
        public function mb($args,$context){ //do I have to inject it?
            if($args=="args2"){
                $context->important();
                return "<br>".$args." in mb";
            }
        }
        //50 other functions that DONT require paper->important()
    }
    
    class Paper{
    
        public function __construct($vitalString){
            $this->vitalString = $vitalString;
        }
        public function all(){
            $list = ['ma'=>'args1','mb'=>'args2'];
            $objRock = new Rock();
            foreach($list as $meth=>$args){
                if(method_exists($objRock,$meth)){
                    $response = $objRock->{$meth}($args,$this);
                    //can I avoid injecting the instantiating $this, into every function I call if only one needs it?
                    echo $response;
                }
            }
        }
        function important(){
            echo "<br>".$this->vitalString;
        }
    }
    
    $myPaper = new Paper("Super Duper");
    
    $myPaper->all();
    ?>
    

    这是输出

    ma中的args1
    超级双面打印
    args2(单位:mb)

    1 回复  |  直到 10 年前
        1
  •  0
  •   dlporter98    10 年前

    我将进行构造函数注入,而不是像您当前所做的那样进行方法注入,如下所示:

    class Rock{
        private $paper;
    
        public function __construct($paper){
            $this->paper = $paper;
        }
    
        public function ma($args){ 
            return $args." in ma";
        }
    
    
        public function mb($args){ //do I have to inject it?
            if($args=="args2"){
    
                $this->paper->important();
    
                return "<br>".$args." in mb";
            }
        }
        //50 other functions that DONT require paper->important()
    }
    

    在mb方法中,我从

    $context->important();
    

    $this->paper->important();
    

    纸质类现在如下所示:

    class Paper{
    
        public function __construct($vitalString){
            $this->vitalString = $vitalString;
        }
        public function all(){
            $list = ['ma'=>'args1','mb'=>'args2'];
    
            $objRock = new Rock($this); //<-------------------
    
            foreach($list as $meth=>$args){
                if(method_exists($objRock,$meth)){
    
                    $response = $objRock->{$meth}($args); //<-----------------
    
                    //can I avoid injecting the instantiating $this, into every function I call if only one needs it?
                    echo $response;
                }
            }
        }
        function important(){
            echo "<br>".$this->vitalString;
        }
    }
    

    通过构造函数注入,您可以在任何地方使用注入的类,而无需担心将其传递给每个方法,即使该方法不需要它。(此外,函数中包含从未使用过的参数会让人感到困惑。)除非paper类有大量属性保存着天文数字的数据,否则不必担心内存问题。

    构造函数注入方法也很方便,以防您决定添加需要使用纸质类的其他方法——如果您需要,它就在那里。

    顺便说一句,所有对象都是通过引用自动传递的——但这与构造函数注入方法无关。