1.什么是super?什么是this?
super关键字表示超(父)类的意思。this变量代表对象本身。
使用this与super可以解决父类属性被隐藏的情况;
this:
首先它的一个用途是让我们知道此时this所引用的实例域是类对象的实例域,所以我们会经常在Bean模型中看到这类词汇 this.name=name; 这里就是this的一个用途,指向隐藏域参数.
第二个用途是可以利用this引用类中的其它构造函数,但是必须让这个语句出现在构造函数的第一行.
super:
首先它的第一个用途是可以让我们引用超类的方法,我们知道子类是不能引用超类的实例域的,所以我们只能通过超类的方法来引用超类的实例域,所以在这里我们就想到super.这种用途主要用于我们平常覆盖超类的方法时需要用到.
第二个用途其实与this差不多,它可以引用超类的构造函数,而且它也必须出现在构造函数第一行.
2.使用super&this调用成员变量和方法
如果在方法内部也有与类成员属性同名的变量,可以这样来区分它们(以变量名为x为例):
x:代表方法的局部变量
this.x:代表本类的成员属性值
super.x:代表从父类继承下来的但被隐藏的x值
如果子类声明了一个与父类的成员方法同名的成员方法,则称父类的该成员方法被重写或覆盖(overriding)
方法覆盖是Java实现多态性机制的另一种方式。
出现方法覆盖时,同样可通过this和super来区分是父类方法还是子类方法。
方法覆盖规则:
1.方法名、参数个数、对应参数类型一样,也称为方法签名一样;
2.返回值类型一样;
3.子类方法的访问控制较父类方法访问控制修饰更松;
可以使用super访问父类被子类隐藏的变量或覆盖的方法。当前类如果是从超类继承而来的,当调用super.XX()就是调用基类版本的XX()方法。见示例1。
当类中有两个同名变量,一个属于类(类的成员变量),而另一个属于某个特定的方法(方法中的局部变量),使用this区分成员变量和局部变量。见示例2。
例1:
class Person{
protected void print(){
System.out.println("The print() in class Person.");
}
}
public class DemoSuper extends Person{
public void print(){
System.out.println("The print() in class DemoSuper.");
super.print();//调用父类的方法
}
public static void main(String[] args){
DemoSuper ds=new DemoSuper();
ds.print();
}
}
结果:
The print() in class DemoSuper.
The print() in class Person
例2
public class DemoThis{
private String name;
public void setName(String name){
this.name=name;//前一个name是private name;后一个name是setName中的参数。
}
}
3.使用this表示当前调用方法的对象引用
假设你希望在方法的内部获得对当前对象的引用,可使用关键字this。this关键字只能在方法内部使用,表示对“调用方法的那个对象”的引用。见示例3。
例3:
Button bn;
...
bn.addActionListener(this);
4.使用super&this调用构造
super(参数):调用基类中的某一个构造函数(应该为构造函数中的第一条语句)。见示例4。
this(参数):调用本类中另一种形成的构造函数(应该为构造函数中的第一条语句)。 见示例5。
例4:
class Person{
public static void prt(String s) {System.out.println(s);}
Person(){
prt("A Person.");
}
Person(String name){
prt("A person name is:"+name);
}
}
public class Chinese extends Person{
Chinese(){
super();//调用父类构造函数。
prt("A chinese.");
}
Chinese(String name){
super(name);//调用父类具有相同形参的构造函数。
prt("his name is:"+name);
}
public static void main (String[] args){
Chinese cn=new Chinese();
cn=new Chinese("kevin");
cn=new Chinese("kevin",22);
}
}
结果:
A Person.
A chinese.
A person name is:kevin
his name is:kevin
例5:
Point(int a,int b){
x=a;
y=b;
}
Point(){
this(1,1); //调用point(1,1),必须是第一条语句。
}
使用super&this应该注意些什么?
1)调用super()必须写在子类构造方法的第一行,否则编译不通过。每个子类构造方法的第一条语句,都是隐含地调用super(),如果父类没有这种形式的构造函数,那么在编译的时候就会报错。
2)super()和this()类似,区别是,super从子类中调用父类的构造方法,this()在同一类内调用其它方法。
3)super()和this()均需放在构造方法内第一行。
4)尽管可以用this调用一个构造器,但却不能调用两个。
5)this和super不能同时出现在一个构造函数里面,因为this必然会调用其它的构造函数,其它的构造函数必然也会有super语句的存在,所以在同一个构造函数里面有相同的语句,就失去了语句的意义,编译器也不会通过。
6)this()和super()都指的是对象,所以,均不可以在static环境中使用。包括:static变量,static方法,static语句块。
7)从本质上讲,this是一个指向本对象的指针, 然而super是一个Java关键字。
8)子类访问父类构造方法,其格式为 super(<参数>) ,super()可以重载
9)java在执行子类构造方法之前,如果没有用super来调用父类中特定的构造方法,则会先调用父类中没有参数的构造方法。应此,如果父类中只定义了有参数的构造方法,而在子类中又没有用super来调用父类中特定的构造方法,则编译器发生错误。解决方法:在父类中构造个空方法,例如 public abc(){};