<?php class Person {
private  $name;
private  $age;
private  $gender;

Function __construct($name, $age, $gender) {
$this->name = $name;
$this->age = $age;
$this->gender = $gender;
}

Function say() {
echo "{$this->name}, {$this->age}, {$this->gender}.<br>";
}

Function study() {

}
}

class Student extends Person {
Function study() {
echo "{$this->name} is studying now";
}
}

$s = new Student("helo", 20, "male");
$s->say();
$s->study();?>
以上是一个继承的例子,Student继承了Person类,因为Person类里的属性全都是private,所以Student类里这些属性不可见,当我调用$s->say();的时候,输出"helo, 20, male.",我的理解是,子类继承了父类的构造方法,而PHP是弱类型的,构造方法里现声明了三个属性并被赋值,所以say方法可以输出结果,但是当我调用$s->study();的时候,输出为"is studying now",helo没有输出,这个是为什么?既然子类继承了父类的构造方法,并且在构造方法中声明并赋值了三个参数,那为什么say可以正确输出,study方法却不行呢?
请大家帮我解答一下。

解决方案 »

  1.   

    在$s->say调用的是父类的say方法,因此对父类中的private成员有访问权限;而$s->study调用的是子类自己的方法,无法对父类的private成员进行访问。子类一般需要自己的构造函数。
      

  2.   

    是的,在你的示例中如果把name设为public或者protected应该就能打印出来了,因为这样可以被子类继承到属性。
      

  3.   

    你这个地方就设计到了class中的访问权限控制,这个是访问权限说明:
    a、默认的是public(公共),即当你没有为属性和方法指定访问修饰时就默认为public的。而这些public的项目在类内类外都可以访问。
       b、private(私有)访问修饰,意味着被修饰的项只能在类中被访问。如果你没使用__get()和__set(),就最好给每个属性都加上 private修饰。也可以给方法加private修饰,例如一些只在类中才用到的函数。private修饰的项不能被继承(更多详细内容会在本章后续部分提到)。
       c、protected(保护)修饰的项能在类及其子类中访问。同样更多详细内容会在本章后续部分提到。现在暂时可以把protected看成界于public和private之间的修饰你在类Person 中将属性name定义为了private了,并且在类中你没有为每个私有属性提供get和set的方法,
    那么在Student类中是调用了$this->name这个值的
      

  4.   

    你已经知道因为Person类里的属性全都是private,所以Student类里这些属性不可见
    所以Student类的study方法不能访问Person类的private属性
      

  5.   


    但是我用子类的引用调用父类的方法,可以访问Person类的属性,就是说,say这个方法没有在子类中重写,那么在子类中调用的时候,他不会方法子类中的属性?
      

  6.   


    say这个方法等于说不属于Student类,而只属于父类?
      

  7.   

    父类的方法并不是复制到子类中,只是可能对子类开放而已,你写的方法都没有指定权限修饰符(private or protectd or public),默认为public,对子类来说是可访问的。
      

  8.   

    private是私有成员,只能自己访问使用。