在PHP中从成员函数访问私有变量

在PHP中从成员函数访问私有变量,php,oop,exception,Php,Oop,Exception,我从Exception派生了一个类,基本上是这样的: class MyException extends Exception { private $_type; public function type() { return $this->_type; //line 74 } public function __toString() { include "sometemplate.php"; retur

我从
Exception
派生了一个类,基本上是这样的:

class MyException extends Exception {

    private $_type;

    public function type() {
        return $this->_type; //line 74
    }

    public function __toString() {

        include "sometemplate.php";
        return "";

    }

}
然后,我从
MyException
中得出如下结论:

class SpecialException extends MyException {

    private $_type = "superspecial";

}
如果我从一个函数中抛出新的SpecialException(“bla”),捕获它,然后转到
echo$e
,那么
\uu toString
函数应该加载一个模板,显示该模板,然后实际上不向echo返回任何内容

这基本上就是模板文件中的内容

<div class="<?php echo $this->type(); ?>class">

    <p> <?php echo $this->message; ?> </p>

</div>

命名受保护的变量:

* Public: anyone either inside the class or outside can access them
* Private: only the specified class can access them. Even subclasses will be denied access.
* Protected: only the specified class and subclasses can access them

您需要将访问权限设置为受保护。Private意味着它只能从自己的类中访问,不能被继承。Protected允许将其保存,但仍然无法从类外直接访问它。

如果查看文档,隐藏在注释中的是:

//我们可以重新声明public和protected方法,但不能声明private

你应该让它
受保护
来做你想做的事情

顺便说一句,看起来您只是将其设置为类名-您可以使用:


在构建继承类时,确实应该将accessmodifier更改为
受保护的


不过要多加一分;不要使用
return“”
但只需使用
返回

只是一个如何访问私有财产的示例

<?php
class foo {
    private $bar = 'secret';
}
$obj = new foo;


if (version_compare(PHP_VERSION, '5.3.0') >= 0)
{

      $myClassReflection = new ReflectionClass(get_class($obj));
      $secret = $myClassReflection->getProperty('bar');
      $secret->setAccessible(true);
      echo $secret->getValue($obj);
}
else 
{
    $propname="\0foo\0bar";
    $a = (array) $obj;
    echo $a[$propname];
}
在这里查看我的答案:


从PHP5.4开始,您可以使用预定义的
闭包
类将类的方法/属性绑定到甚至可以访问私有成员的增量函数

例如,我们有一个带有私有变量的类,我们希望在类之外访问它:

class-Foo{
private$bar=“Foo::bar”;
}
PHP5.4+

$foo=新foo;
$getFooBarCallback=函数(){
返回$this->bar;
};
$getFooBar=$getFooBarCallback->bindTo($foo,'foo');
echo$getFooBar();//打印Foo::Bar
从PHP7开始,您可以使用新的
Closure::call
方法将obect的任何方法/属性绑定到回调函数,即使对于私有成员也是如此:

PHP7+

$foo=新foo;
$getFooBar=函数(){
返回$this->bar;
};
echo$getFooBar->call($foo);//打印Foo::Bar

无法在类之外访问$this。 相反,需要调用类的实例。
然后,访问类中将返回消息的函数

通过使用\Closure可以实现以下目的:

$reader=函数($object,$property){
$value=\Closure::bind(函数()使用($property){
返回$this->$属性;
},$object,$object)->\uu invoke();
返回$value;
};
$myClass=新的myClass();
$property=$reader($myClass,'yourProperty');
echo$property;//将显示属性的值

注意:在PHP中,受保护的
意味着你的父母也可以访问他们。好吧,我这样做了——但现在我不能使用
$this->消息
——没有错误,它只是不显示任何内容。。。为什么?不管怎样,我在父构造函数中设置了
$message
,而不是
$this->message
。此外,我意识到我没有提供关于如何设置消息的实际实现细节。我的回答是肯定的,但是如果我更改了(php)类名,我就必须更改(css)类名,而且,如果我想在异常模板文件中使用更多信息,我可能会像添加“type”属性那样添加它。您的额外点会导致致命错误,我已经尝试过--
\uu toString()
必须返回字符串啊,对不起!我查看了你的__; toString函数。。刚刚看到你什么都没回。你完全正确!让_toString()返回一个空字符串是非常难看的。我真的看不出这种东西有什么用处。但是你是对的,\uuuToString()必须返回一个字符串。正如我在下面写的:让\uuuToString()返回一个空字符串是非常丑陋的。我真的看不出这类东西有什么用处。异常的_toString()的空返回更令人怀疑。我怎样才能为setter做这里的“else”呢?程序员会给出一个代码片段来澄清问题。对吗?导游。非常感谢。
<?php
class foo {
    private $bar = 'secret';
}
$obj = new foo;


if (version_compare(PHP_VERSION, '5.3.0') >= 0)
{

      $myClassReflection = new ReflectionClass(get_class($obj));
      $secret = $myClassReflection->getProperty('bar');
      $secret->setAccessible(true);
      echo $secret->getValue($obj);
}
else 
{
    $propname="\0foo\0bar";
    $a = (array) $obj;
    echo $a[$propname];
}