PHP面向对象程序设计重载(overloading)操作详解(4)

运行结果为:

a1->p1:1
a1->p1:该属性不存在!

下面的例子中,声明一个Person类,并将所有的成员属性设置成private的。在类中添加自定义的“__isset()”和“__unset()”两个方法。在类外部使用“isset()”和“unset()”函数时,会自动调用这两个方法。代码如下:

<?php
class Person{
  private $name; //此属性被封住
  private $sex;
  private $age;
  function __construct($name='', $sex='男', $age){
    $this->name = $name;
    $this->sex = $sex;
    $this->age = $age;
  }
  private function __isset($propertyName){  //需要一个参数,是测定的私有属性的名称
    if($propertyName == 'name'){
      return false;  //返回假,不允许在类外部测定name属性
    }
    return isset($this->$propertyName);  //这里propertyName要加$符,因为这是参数,不是属性
  }
  private function __unset($propertyName){
    if($propertyName == 'name')
      return; //退出方法,不允许删除对象中的name属性
    unset($this->$propertyName); //这里propertyName要加$符
  }
  public function say(){
    echo "名字:" . $this->name . ",性别:" . $this->sex . ",年龄:" . $this->age . "<br />";
  }
}
$person = new Person("yeoman", "男", 23);
var_dump(isset($person->name));  //输出bool(false),不允许测定name属性
var_dump(isset($person->sex)); //输出bool(true),存在sex私有属性
var_dump(isset($person->age)); //输出bool(true),存在age私有属性
var_dump(isset($person->id)); //输出bool(false),测定对象中不存在id属性
unset($person->name); //删除私有属性name,但在 __unset()中不允许删除
unset($person->sex);  //删除对象中的私有属性sex,删除成功
unset($person->age);
$person->say();  //对象中的sex和age属性被删除,输出:名字:yeoman,性别:,年龄:
?>

运行结果:

boolean false
boolean true
boolean true
boolean false
名字:yeoman,性别:,年龄:

方法重载

当对一个对象不存在的实例方法进行“调用”时,会自动调用类中的__call()这个魔术方法;

当对一个类不存在的静态方法进行“调用”时,会自动调用类中的__callstatic()这个魔术方法。

例子:直接调用不存在的方法

<?php
ini_set('display_errors',1);
class A{
}
$a = new A();
$a->f1(); //不存在的方法
?>

会报错,报错内容为:

Fatal error: Uncaught Error: Call to undefined method A::f1()

对上面报错作“优雅处理”: