在不使用类的情况下返回具有__toString功能的对象

时间:2016-10-14 10:35:45

标签: php oop

我想将一个对象返回给调用者,该调用者在回显时打印一个字符串,但也具有可以访问的属性。如果没有预定义的类和/或大量代码漏洞,我怎样才能实现这一目标?

$obj = func();   // an object should be returned, where: 
echo $obj->prop; // 1) the object has properties
echo $obj;       // 2) echoing the object itself should echo a specific string

使用类的工作示例:

<?

class obj {

  var $head;
  var $body;

  function __construct($head, $body) {
    $this->head = $head;
    $this->body = $body;
  }

  function __toString() {
    return $this->body;
  }

}

function blah() {

    return new obj("My head", "My body");

}

$response = blah();
echo "$response->head and $response\n";

?>

可能失败的伪尝试:

<?

function blah() {

    $head = "My head";
    $body = "My body";

    return (object) array(
        "head" => $head,
        "body" => $body,
        "__toString" => function() {
            return $body;
        },
    );
}

$response = blah();
echo "$response->head and $response\n";

?>

2 个答案:

答案 0 :(得分:2)

一个对象是一个类的实例......你不能绕过这个事实。

如果您想对该课程加以限制 - 当然,请继续。您似乎需要以下内容:


final class Response
{
    private $head, $body;

    public function __construct($head, $body)
    {
        $this->head = $head;
        $this->body = $body;
    }

    public function __toString()
    {
        return $this->body;
    }

    public function __get($property)
    {
        return isset($this->$property)
            ? $this->$property
            : null;
    }
}

您只能阅读它的echo及其final中的属性,因此无法对其进行扩展。

答案 1 :(得分:2)

虽然@Narf是正确的,但对象类的一个实例,你可以在PHP 7中做Anonymous Classes这样的事情。

来自PHP docs

<?php

$util->setLogger(new class {
    public function log($msg)
    {
        echo $msg;
    }
});

如果您有兴趣将此方法应用于您的情况,您可以尝试以下内容:

<?php

$response = new class {
    public function setBody($body) {
        $this->body = $body;
    }

    public function setHead($head) {
        $this->head = $head;
    }

    public function __toString() {
        return (string) $this->body;
    }
};

$response->setHead('200 OK');
$response->setBody('Lorem Ipsum');

echo "$response->head and $response"; // 200 OK and Lorem Ipsum