【问题标题】:passing function by reference from within class从类中通过引用传递函数
【发布时间】:2013-06-21 11:03:55
【问题描述】:

我试图通过引用另一个函数来传递一个函数(来自同一个类)以执行该函数,但它似乎不起作用。我可以在课堂外但不能在课堂内这样做:有没有办法正确地做到这一点?

class test {
  function test() {
    $this->check(1==2, &$this->t(), &$this->f()); 
  }

  function check($statement, $true, &$false) {
    if(eval($statement)) {
      $true;
    }
    $false;
  }

  function t() {
    print "true";
    return true;
  }

  function f() {
    print "false";
    return false;
  }
}

【问题讨论】:

  • 你有没有想过你做错了什么?如果您想将一个函数作为 CALLBACK 传递给另一个函数,则不要通过将函数作为引用传递来实现。如果将函数作为引用传递,则不是在引用该函数,而是在引用它的返回值。 Classic XY problem
  • 你能示范一下你在课外是怎么做的吗?

标签: php class oop pointers reference


【解决方案1】:

在调用时通过引用传递已被弃用(实际上自 5.4 起已删除):

从 PHP 5.3.0 开始,当您在 foo(&$a); 中使用 & 时,您将收到一条警告说“调用时传递引用”已被弃用。并且从 PHP 5.4.0 开始,调用时传递引用已被删除,因此使用它会引发致命错误。

From php's docs.
传递对布尔值的引用也没有真正意义。理论上,PHP 引用占用的内存与 C 指针(4 个字节)相同,布尔值可能是一个(短)int,只需要 2 个字节。如果有的话,我会说你会产生更多的开销。

如果您通过引用另一个函数/方法来传递对象或数组,则必须相应地定义函数:

function doStuff_byRef(array &$arg)
{
    $arg[] = 'add new stuff';
}

通过引用传递函数,就像在 JS 中所做的那样,在 PHP 中是不可能的。但是,您可以定义一个函数返回一个值,而是返回对其返回值的引用:

public function &getPropertyRef()
{
    return $this->property;
}

但是,在你的情况下,我会这样做:

$this->check(1==2, 't', 'f');//pass method names
private function check($stmt, $func1, $func2)
{
    //don't use eval, btw
    if ($stmt)
    {
        return $this->{$func1}();
    }
    return $this->{$func2}();
}

或者,更灵活:

$this->check(1==2, array($this, 't'), array($this, 'f'));//pass method names
private function check($stmt, array $func1, array $func2)
{
    //don't use eval, btw
    if ($stmt)
    {
        return call_user_func_array($func1);
    }
    return call_user_func_array($func2);
}

我想,如果你的 PHP >= 5.3,你可以使用闭包实例:

private function check($stmt, Closure &$func1, Closure &$func2)
{
    return $stmt ? $func1() : $func2();
}

那么,你可以这样做:

$functionReference = function()
{
    echo 'true';
    return true;
};
$functionRef2 = function()
{
    echo 'false';
    return false;
};
$this->check(true, $functionReference, $functionRef2);

但这增加了更多的开销:PHP 闭包只是添加到语言中的东西之一,不应该存在。它在编译时创建Closure 类的实例,然后通过引用传递该对象。老实说,在您的情况下,最好的方法是我的第一个建议,恕我直言 ($this->{$func1}();)

【讨论】:

  • 还有其他方法吗?
  • @user784446:编辑了我的答案。此外,请阅读有关 PHP 引用如何工作的 php 文档。 public function &foo()public function foo(&ref) 仍然有效。检查符合您要求的套件
  • @user784446:扩展了一些 JS 风格的函数引用(PHP 中的闭包实例),以及为什么我不会在这种特殊情况下使用它们
  • 谢谢!关于使用 call_user_func_array 的示例,由于某种原因,消息被打印了两次,从而给人以某种方式被调用两次的印象。我只调用过一次函数。
  • 啊,我的错:正在使用与类同名的函数。
猜你喜欢
  • 2022-01-11
  • 1970-01-01
  • 1970-01-01
  • 2020-01-25
  • 1970-01-01
  • 2020-10-02
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多