目录
? ? ? ? 抽象类是对于一类相同的具体概念的抽象。
? ? ? ? 抽象类和抽象方法都使用“abstract”关键字来修饰。
????????抽象类不能被实例化,不能通过构造方法创建实例,只能通过子类创建实例时调用,抽象方法没有方法体。
? ? ? ?抽象方法和抽象类的使用规则:
? ? ? ? 一个抽象类可以有多个抽象方法,也可以含有已经实现的方法,但不能通过抽象类调用该方法,有抽象方法的类一定是抽象类。
(1)一般来说,实现类继承于抽象类,来实现父类的抽象方法
(2)或者实现类通过接口,实现接口中的抽象方法。
(3)抽象类与其他类的关系在于,抽象类不能创建自己的对象。
? ? ? ? 注意:
(1)abstract不能用来修饰变量和构造方法
(2)abstract修饰的方法,只有在重写后才获得意义,抽象方法也不能定义为private,也不能和static、final同时修饰同一方法。
(1)抽象类--动物类
public abstract class Animal {
private String name;
public Animal(){};
public Animal(String name)
{
this.name=name;
}
public String getName()
{
return this.name;
}
public void setName(String name)
{
this.name=name;
}
public abstract void action();
}
(2)子类--马类
public class Horse extends Animal{
public Horse (String name)
{
super(name);
}
public void action()
{
System.out.println(this.getName()+"在奔跑");
}
}
? ? ? ? 子类继承抽象类,要用extends连接父类
? ? ? ? 子类的构造方法,如果调用父类的方法,则使用super(局部变量)?
(3)子类--鸟类
public class Bird extends Animal{
public Bird(String name)
{
super(name);
}
public void action()
{
System.out.println(this.getName()+"在飞翔");
}
}
(4)测试类
public class Test {
public static void main(String[] args)
{
Animal a;
a=new Horse("马"); //马的实例
a.action();
a=new Bird("鸟"); //鸟的实例
a.action();
}
}
? ? ? ? 注意!抽象类变量可以指向其子类,但不能实例化一个抽象类?
????????输出:
马在奔跑
鸟在飞翔
? ? ? ? 由于Java只支持单一继承,不支持多重继承,即一个类只能继承一个父类,这一缺陷可以通过接口来弥补,所以Java允许一个类实现多个接口
? ? ? ? 接口的访问符可以是public或者缺省(缺省代表权限范围为当前包),一个接口可以继承多个父接口,但接口只能继承接口,不能继承类。
? ? ? ? 接口内可以包含静态常量、抽象方法、内部类、内部接口以及枚举,在Java8 之后可以定义默认方法,类方法。
? ? ? ? 接口内的常量、方法默认为public,成员属性默认为public static final(全局静态常量)
? ? ? ? 接口不可以直接实例化,但可以通过使用实现类实现接口,关键字为implements,注意s。一个类可以实现若干接口,用逗号隔开,这个类也要同时实现若干接口的所有抽象方法,否则该类应被定义为抽象类,实现抽象方法是需要重写方法,添加@override。
? ? ? ? 当一个类实现某个接口时,该类也将获得接口中定义的常量、方法。
(1)接口类--Animal类
public interface Animal {
public int MAX=100;
public void makeSound();
}
(2)实现类--Dog类
public class Dog implements Animal{
@Override
public void makeSound()
{
System.out.println("Woof!");
}
}
(3)测试类--Test类
public class Test {
public static void main(String[] args)
{
Dog gauss = new Dog(); //也可以写作Animal gauss = new Dog();
System.out.println("The Dog`s speed: "+gauss.MAX);
gauss.makeSound();
}
}
? ? ? ? 在输出接口类中的常量时,可以用"类名.常量" 或 "对象名.常量"。
? ? ? ? 接口可以指向类的实例对象,这也是多态的一种体现,也就是上面的Animal gauss = new Dog()。
????????输出:
The Dog`s speed: 100
Woof!
? ? ? ? ?接口继承可以支持多继承,并且可以获得父接口定义的所有抽象方法和常量。
? ? ? ? 一个接口继承多个接口时,多个接口跟在extends关键字后,并使用“,”进行间隔。
(1)接口及其实现类
? ? ? ? 这里通过省略public,省略访问符的形式,可以在同一个文件下写多个接口,但坏处在于访问限制为当前包。
? ? ? ? 下面接口IntefaceC继承于InterfaceA和InterfaceB两个接口,并通过Demo类实现InterfaceC的接口。
interface InterfaceA {
int valueA = 10;
void testA();
}
interface InterfaceB
{
int valueB = 20;
void testB();
}
interface InterfaceC extends InterfaceA,InterfaceB
{
int valueC = 30;
void testC();
}
public class Demo implements InterfaceC
{
public void testA()
{
System.out.println("这是testA方法,valueA: "+valueA);
}
public void testB()
{
System.out.println("这是testB方法,valueB: "+valueB);
}
public void testC()
{
System.out.println("这是testC方法,valueC: "+valueC);
}
}
(2)测试类
? ? ? ? 首先通过接口直接调用接口中定义的常量,另外通过接口实现类调用接口中定义的常量。
public class Test {
public static void main(String[] args)
{
System.out.println("通过接口调用,valueA: "+InterfaceA.valueA);
InterfaceC ic = new Demo();
ic.testA();
ic.testB();
}
}
????????输出:?
通过接口调用,valueA: 10
这是testA方法,valueA: 10
这是testB方法,valueB: 20
(1)接口和抽象类都不能被实例化,需要被其他类实现或继承
(2)接口和抽象类的类型变量都可以指向其实现类或子类的实例对象
(3)接口和抽象类都包含抽象方法,实现接口和继承抽象类都需要实现其抽象方法。
????????主要区别体现在设计目的上:
(1)接口是一种规范,类似一种总纲,是系统都应遵循的标准,来实现各模块的耦合和通信
(2)抽象类体现一种模块化设计,一般作为系统实现中的中间产品,需要进一步的完善。
? ? ? ? 其他区别:
(1) 接口不能为普通方法提供方法实现,抽象类可以为普通方法提供方法实现。
(2)接口定义变量默认为public static final,必须赋予初值,实现类不能重定义,抽象类的变量可以在普通类中重新定义。
(3)接口中定义方法默认时是public限定,抽象类定义方法默认是缺省的。
(4)接口不包括构造方法,抽象类包括构造方法。
(5)一个类只能继承一个父类,但一个类可以实现多个接口,接口也可以实现多个接口。
? ? ? ? 语法: 子类 instanceof 父类
? ? ? ? 上面语句返回该子类是否继承于父类,是则返回true,否则返回false,用于判断继承关系。
参考书籍:《Java 8 基础应用与开发》QST青软实训编