this关键字
Java提供一个关键字this来指代当前对象,用于在方法中访问对象的其他成员。
- 通过this关键字调用成员变量,解决与局部变量名称冲突问题:
class Person{
String name;
public Person (String name) {
this.name=name; //将局部变量name赋值给成员变量name.
}
}
- 通过this关键字调用成员方法:
class Person{
public void mouth() {
}
public void speak() {
this.mouth(); //此处this.可以省略。
}
}
- 通过this关键字调用构造方法:
class Person{
public Person(){
System.out.println("无参的构造方法被调用了...");
}
public Person(int age){
this(); //通过实例化有参构造方法调用无参构造方法。
System.out.println("有参的构造方法被调用了...");
}
}
public class Example{
public static void main(String[] args){
Person p=new Person(20);
}
}
在使用this调用类的构造方法时,应注意以下几点:
1.只能在构造方法中使用this调用其他构造方法,不能在成员方法中使用。
2.在构造方法中,使用this调用构造方法的语句必须是该方法的第一条语句,且只能出现一次。
public Person(int age){
System.out.println("有参的构造方法被调用了...");
this(); //语法错误:Constructor call must be the first statement in a constructor
}
3.不能在一个类的两个构造方法中使用this互相调用。
class Person{
public Person(){
this(18);
System.out.println("无参的构造方法被调用了...");
}
public Person(int age){
this();
System.out.println("有参的构造方法被调用了...");
}
//语法错误:Recursive constructor invocation Person()
}
super关键字
当子类重写父类的方法后,子类对象将无法直接访问父类被重写的方法。为此Java提供了super关键来访问父类的成员。
- 使用super关键字调用父类的成员变量和成员方法:
class Animal{
String name="动物";
void shout() {
System.out.println("动物发出声音");
}
}
class Dog extends Animal{
String name="狗";
void shout() {
super.shout(); //super.成员变量调用父类成员变量
}
void printName(){
System.out.println("nema=" + super.name); //super.成员方法([参数1,参数2...])调用父类成员方法([参数1,参数2...])
}
}
public class Example(){
public static void main(String[] args){
Dog dog=new Dog();
dog.shout();
dog.printName();
}
}
- 使用super关键字调用父类的构造方法:
class Animal{
public Animal(String name) {
System.out.println("我是" + name);
}
}
class Dog extends Animal{
public Dog(){
super("哈士奇");
}
}
public class Example{
public static void main(String[] args){
Dog dog=new Dog();
}
}
需要注意:
- 通过super调用父类构造方法的代码必须位于子类构造方法的第一行,并且只能出现一次。否则报出异常: Constructor call must be the first statement in a
constructor- 在定义一个类时,如果没有特殊要求,当定义了有参构造方法后,尽量在类中再显式地定义一个无参构造方法。例如:
class Animal{
public Animal(String name) {
System.out.println("我是" + name);
}
}
class Dog extends Animal{
public Dog(){
//super("哈士奇");
/*
注解后,报出异常:Implicit super constructor
Animal() is undefined. Must explicitly invoke another constructor
原因: 在子类的构造方法中一定会调用父类的某个构造方法,此时可以在子类的构 造方法中通过super关键字指定调用父类的哪一个构造方法,
如果没有指定,在实例化子类对象时,会默认调用父类无参的构造方法。
*/
}
}
public class Example{
public static void main(String[] args){
Dog dog=new Dog();
}
}
final关键字
1. final关键字修饰类
Java中的类被final关键字修饰后,该类将不可以被继承,也就是不可以派生子类。
final class Animal{
}
class Dog extends Animal{ //编译报错:The type Dog cannot subclass the final class Animal
}
2. final关键字修饰方法
当一个类的方法被final关键字修饰后,这个类的子类将不能重写该方法.
class Animal{
public final void shout() {
}
}
class Dog extends Animal{
public void shout() { //编译报错:Cannot override the final method from Animal
}
}
3. final关键字修饰变量
被final修饰的变量只能被赋值一次,也就是说final修饰的变量一旦被赋值,其值不能改变。
public class Example{
public static void main(String[] args){
final int num=2;
num=4; //编译报错:he final local variable num cannot be assigned. It must be blank and not using a compound assignment
}
}
final修饰的实例变量必须手动初始化,即不能使用系统的默认初始值;
final修饰的实例变量一般与static联合使用,称为常量。
4.final修饰的引用
final修饰的引用一旦指向某个对象,则不能重新指向其他对象,但该引用所指向对象的内部数据可以改变。
static 关键字
1. 静态变量
希望某些特定的数据在内存中只有一份,而且能够被一个类的所有实例对象所共享.
class Student {
static String schoolName; // 声明静态变量schoolName
}
public class Example {
public static void main(String[] args) {
Student stu1 = new Student();
Student stu2 = new Student();
Student.schoolName = "清华大学";
System.out.println("我是" + stu1.schoolName+"的学生");
System.out.println("我是" + stu2.schoolName+"的学生");
}
}
注意:static关键字只能修饰成员变量,不能用于修饰局部变量。
2. 静态方法
希望在不创建对象的情况下就可以调用某个方法.
class Person {
public static void say() { // 定义静态方法
System.out.println("Hello!");
}
}
public class Example {
public static void main(String[] args) {
Person.say(); // “类名.方法”的方式调用静态方法
Person person = new Person();
person.say(); // “实例对象名.方法”的方式来调用静态方法
}
}
注意:在一个静态方法中只能访问用static修饰的成员,原因在与没有被static修饰的成员需要先创建对象才能访问,而静态方法在被调用是可以不创建任何对象。
3. 静态代码块
在类被加载时,静态代码块只会执行一次.
class Person{
static {
System.out.println("执行了Person类中的静态代码块");
}
}
public class Example{
static{
System.out.println("执行了测试类中的静态代码块");
}
public static void main(String[] args){
Person p1 = new Person();
Person p2 = new Person();
/*
JVM虚拟机首先加载类EXample,在加载类的同时就会执行该类的静态代码块,紧接着会调用main()方法,
在main()方法中创建了两个Person对象,但在两次实例化对象的过程中,静态代码块中的内容只输出一次.
*/
}
}
abstract关键字
1.abstract修饰类:抽象类
此类不能实例化;
抽象类中一定有构造器,便于子类实例化时调用;
开发中,都会提供抽象类的子类,让子类对象实例化,完成相关的操作。
2.abstract修饰方法:抽象方法
抽象方法只有方法的声明,没有方法体;
包含抽象方法的类,一定是一个抽象类。反之,抽象类中可以没有抽象方法的。
若子类重写了父类中的所有的抽象方法后,此子类方可实例化;若子类没有重写父类中的所有的抽象方法,则此子类也是一个抽象类, 需要使用abstract修饰