OOP:通过匿名函数将方法从同一类获取到另一方法

时间:2018-07-17 04:42:00

标签: php class oop methods

我是面向对象的PHP的新手,所以我不确定我的问题到底是什么,但这就是问题所在:

我创建了一个WordPress插件,该插件在由另一个插件创建的特定自定义帖子类型上添加了一堆metabox。在我的主题中,我需要获取所有自定义的元数据,但是需要获取很多内容,并且通常需要使用某些条件等等。因此,我创建了一堆辅助函数来简化它。问题是所有这些函数的名称都很麻烦,因此我将它们放在插件的类中以简化操作,而我的问题是组合它们时遇到麻烦。不管有没有可能,希望您能为您提供帮助...

因此大多数辅助函数(现在是类方法)看起来像这样:

public function metabox_wrapper( $code ) {

    $info = get_post_meta( ID, 'blah', true);

    if ( $info ) {
        code( $info );
    }

}

然后在主题文件中使用:

global $Other_Plugins_Global // Created by the other plugin.
$class = new Class( $Other_Plugins_Global );

$class->metabox_wrapper( function( $info ) {
?>

    <div>
        <?php echo $info; ?>
    </div>

<?php
});

以上内容当前有效-如果存在blah元数据,它将显示当前帖子中的blah元。另一个插件的全局变量包含自定义帖子类型信息(因此也包含元信息),因此我将其传递给类实例,使用类中的方法来管理所有条件和其他复杂的东西,然后在主题文件,这样可以对条件素材进行预先安排,并可以在主题的其他位置以相同的方式使用。

但是,这是麻烦所在:在某些情况下,我想要类似的东西

if (
    Do this
    if (
        Also do this
    )
)

但是,这(以及我尝试过的所有类似方法)均无效:

global $Other_Plugins_Global
$class = new Class( $Other_Plugins_Global );

$class->metabox_wrapper( function( $info ) {
?>

    <div>
        <?php echo $info; ?>
    </div>

    <?php
    $class->other_metabox_wrapper( function( $stuff ) {
    ?>

        <div>
            <?php echo $stuff; ?>
        </div>

    <?php
    });

});

所以我的问题是...有没有办法可以在彼此内部使用这些包装器函数?我尝试将它们设置为静态,并在主题中使用::,我尝试了一些花哨的可变体操,这些体操都行不通,如果真的会很丑,我几乎举起了一个恶魔,试图从方法内部调用全局变量...因此,目前为止,我什至不知道Google应该怎么做。

显然,对于这个特定示例,我可以只使用if(){},但是条件逻辑通常具有多个条件和其他半复杂的东西,因此将其分开并能够在多个条件下使用将很有帮助。主题周围的地方。

我要说的是,如果这是一个愚蠢的问题,并且您知道一种完全不同且更优雅的方式来完成我所描述的内容,那么我就会不知所措。

非常感谢您的帮助。

2 个答案:

答案 0 :(得分:1)

问题不在于OOP领域,而在于功能和功能范围领域。您会看到,创建anonymous function时,它具有自己的作用域-可访问的变量范围。在大多数语言中,匿名函数将其创建时所在的范围括起来,从而创建一个closure,这意味着它可以访问父范围中所有变量的副本。在PHP中不是这种情况,因此要从匿名函数中访问$class变量,应使用use$class->metabox_wrapper(function($info) use ($class) {

另一种方法是使用Closure::bind()将上下文绑定到匿名函数:

public function metabox_wrapper($code) {
    $info = get_post_meta(ID, 'blah', true);

    if ($info) {
        $code = Closure::bind($code, $this);
        $code($info);
    }
}

然后,您可以在匿名函数内使用$this

$class->metabox_wrapper(function($info) {
?>
    <div>
        <?php echo $info; ?>
    </div>

    <?php
    $this->other_metabox_wrapper(function($stuff) {
    ?>
        <div>
            <?php echo $stuff; ?>
        </div>
    <?php
    });
});

但是要告诉你一个事实,我同意@CrisanLucian。以这种方式将代码与HTML混合并不是最好的编程方法。

答案 1 :(得分:0)

首先,您必须阅读一些编码标准文章 1. https://www.tutorialspoint.com/php/php_coding_standard.htm

  1. 尝试将PHP代码和HTML分开;使用Twig代替PHP使生活更加轻松 https://aristath.github.io/blog/using-twig-in-wordpress

  2. 当您需要更多帮助(挂钩)功能时,最好将它们分组到一个类中,或者创建一个Helper目录结构并为每个作用域创建一个文件。 (例如:修剪字符串,调整图像大小会创建不同的文件)

  3. 在创建Helpers之后,请尝试不要将HTML放入其中;助手应该返回一个值(布尔值)。
    例如showCampaign()=>将返回True;
       HTML页面/ TWIG页面 {{if(showCampaign())}}    //此处是HTML代码 {{endif}}

  4. 如果需要重构过多的if / else语句,请检查上面的链接或另一个示例:https://carlalexander.ca/mastering-php-conditionals/

  5. 幸福的生活!