目录
一、抽象类
1、抽象的定义
关于抽象类:
在JAVA中,所有的对象都是通过类来描绘的,而并非所有的类都是来描绘对象的,倘若一个类无法明确地描绘一个具体的对象,相对地我们称此种类为抽象类。
无法明确描绘一个具体的对象,称为抽象
2、抽象方法
(1)理解
将共性的行为(方法)抽取到父类之后,发现父类无法明确、具体地描述该方法的实现逻辑,此方法可定义为抽象方法。
换而言之,抽象父类给了一个方法范式,但这个方法范式没有具体的内容,此种范式被每一个子类继承,对于此种方法范式,每一个子类又有自身独特的实现逻辑来实现此方法。
(2)注意
*抽象方法没有方法体
下面来让我们看看代码示例:
/**
* @author Tweek
*/
public abstract class Subject {
/**
* This abstract method is used to set way of learning different Subjects
*/
public abstract void learn();//抽象类中的抽象方法
}
public class English extends Subject{
@Override//重写抽象父类中的learn方法
public void learn() {
System.out.println("Learning English you need to speak and listen");
}
}
public class Math extends Subject {
@Override//重写抽象父类中的learn方法
public void learn() {
System.out.println("Learning Math you need to Think more and practice more");
}
}
public class AbstractDemo {
/**
* 测试类
*/
public static void main(String[] args) {
Subject english = new English();
Subject math = new Math();
english.learn();
math.learn();
}
}
控制台输出:
Learning English you need to speak and listen
Learning Math you need to Think more and practice more
3、抽象类的特点
1、抽象类与抽象方法都需要abstract修饰,都如果一个类中存在抽象方法,那么该类就必须声明为抽象类。
2、抽象类不能实例化,即抽象类不能创建对象。因为抽象类中的抽象方法没有方法体,创建对象调用抽象方法无意义,故抽象类不能实例化。
3、抽象方法存在构造方法。因为抽象类可以被子类继承,故构造方法的作用是为子类提供访问入口,使其能通过super访问抽象父类。
4、抽象类中可以存在普通带有逻辑的方法。其存在意义在于,被子类继承使用。
5、抽象类的子类,需满足:
(1)重写抽象父类中的所有抽象方法(作为方法范式)
(2)子类本身为抽象类
下面让我们来看看代码示例,用于帮助我们了解抽象类的特点:
/**
* @author Tweek
*/
public abstract class Employee {
/**
* This abstract method is used to represent the coders and managers
*
*/
private String name;
private int age;
private double salary;
/**
* 抽象类的无参构造方法,用于初始化,给子类提供访问途径
*/
public Employee() {
}
/**
*抽象类的有参构造方法,被子类继承使用
*/
public Employee(String name, int age, double salary) {
this.name = name;
this.age = age;
this.salary = salary;
}
/**
* 抽象方法 work,在Employee中作为work规范,要求每一个子类都有一个work方法,且方法内容可以自定
*/
public abstract void work();
/**
*
* 普通方法,被子类继承使用
*/
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public int getAge() {
return age;
}
public void setAge(int age) {
this.age = age;
}
public double getSalary() {
return salary;
}
public void setSalary(double salary) {
this.salary = salary;
}
}
public class Manager extends Employee{
/**
* Manager the employee
*/
//private成员变量
private double bonus;
public Manager() {
}
@Override
public void work() {
System.out.println("Manager's Name: "+super.getName()+"----"+"Manager's Age:"+super.getAge()+"----"+"Manager's salary:"+super.getSalary()+"----"+"Manager's bonus"+bonus);
System.out.println("The Manager is assigning works");
}
public Manager(String name, int age, double salary,double bonus) {
super(name, age, salary);
this.bonus=bonus;
}
public double getBonus() {
return bonus;
}
public void setBonus(double bonus) {
this.bonus = bonus;
}
}
public class Coder extends Employee{
/**
* Coder the employee
*/
public Coder() {
}
public Coder(String name, int age, double salary) {
super(name, age, salary);
}
@Override
public void work(){
System.out.println("Coder's Name: "+super.getName()+"----"+"Coder's Age:"+super.getAge()+"----"+"Coder's salary:"+super.getSalary());
System.out.println("The Coder is coding");
}
}
public class Test1 {
/**
* 测试类
* @param args
*/
public static void main(String[] args) {
Manager manager = new Manager("LISI",26,15000,5000);
Coder coder = new Coder("ZHANGSAN",23,15000);
manager.work();
coder.work();
}
}
控制台输出:
Manager's Name: LISI----Manager's Age:26----Manager's salary:15000.0----Manager's bonus5000.0
The Manager is assigning works
Coder's Name: ZHANGSAN----Coder's Age:23----Coder's salary:15000.0
The Coder is coding
4、abstract关键字的冲突
(1)final:被abstract修饰的方法,强制要求子类重写,被 final修饰的方法子类不能重写
(2)private:被abstract修饰的方法,强制要求子类重写,被private修饰的方法子类不能重写
(3)static:被static修饰的方法可以类名调用,类名调用抽象方法没有意思。
二、接口
1、接口的定义
关于接口:
一般认为接口是一种被公共认可的规范标准,是对行为的抽象。我们知道抽象类是对事物进行抽象,即对类抽象,而接口是对行为进行抽象。对于飞机与鸟来说,它们有共同的特性就是会飞,但是它们是不同类型的事物,我们可以给飞机与鸟设计类,但无法给飞行这一特性设计类,那么对于这一行为特性,我们可以将其设定为接口,同样的这是一种对于飞行这一行为来说的规范标准。
2、接口的特点
1、接口用关键字interface来定义
2、接口不能实例化。因为接口内只能有抽象方法,而抽象方法没有方法体,实例化接口调用抽象方法无意义
3、接口与类之间是实现关系,通过implements关键字表现
4、接口的子类(实现类),需满足:
(1)重写接口中的所有抽象方法
(2)子类本身是抽象类
下面是代码示例来初步理解接口:
/**
* @author Tweek
*/
public interface Fly {
/**
* This abstract method is used to represent The action of flying
*/
void fly();
}
public class Plane implements Fly{
/**
* 飞机类
*/
@Override
public void fly() {
System.out.println("I'm a Plane and I can fly!");
}
}
public class Bird implements Fly {
/**
* 鸟类
*/
@Override
public void fly() {
System.out.println("I'm a Bird and I can fly too!");
}
}
public class Test2 {
/**
* 测试类
*/
public static void main(String[] args) {
Fly f = new Plane();
Fly f2 = new Bird();
f.fly();
f2.fly();
}
}
控制台输出:
I'm a Plane and I can fly!
I'm a Bird and I can fly too!
3、接口的成员特点
(1)成员变量
只能是抽象方法,因为系统会默认加入public abstract关键字。
下面是代码示例
/**
* @author Tweek
*/
public interface Fly {
/**
* This abstract method is used to represent The action of flying
*/
void fly();
}
(2)成员方法
只能定义成员变量,因为系统会默认加入三个关键字:public static final。(public可以使用跨包调用检验)
下面是代码示例:
/**
* @author Tweek
*/
public interface Fly {
/**
* This abstract method is used to represent The action of flying
*/
void fly();
int height = 2000;
}
public class Test2 {
/**
* 测试类
*/
public static void main(String[] args) {
Fly f = new Plane();
Fly f2 = new Bird();
f.fly();
f2.fly();
//static修饰的类可以用类名调用数据
System.out.println(Fly.height);
//系统报错无法改变height的数据,为使得代码运行成功故注释掉下面赋值代码
//Fly.height = 100;
System.out.println(Fly.height);
}
}
控制台输出:
2000
(3)构造方法
接口没有构造方法。在接口的实现类中,实现类的super调用,调用的是Object类。
4、接口与类之间的关系
(1)类与类之间
继承关系,只支持单继承,不支持多继承,但可以支持多层继承。
(2)类与接口之间
实现关系,可以单实现,也可以多实现,甚至可以在继承一个类的同时,实现多个接口
(3)接口与接口之间
继承关系,可以单继承,也可以多继承
下面代码示例,能让我们更好的理解接口与类、接口与接口的关系:
/**
* @author Tweek
*/
public interface Fly {
/**
* This abstract method is used to represent The action of flying
*/
void fly();
}
public interface Think {
/**
* first Thinking then doing the rest
* 能思考,才能做其他事情,比如唱歌
*/
void think();
}
public interface Sing extends Think {
/**
* This method is used to represent the action of Singing
*/
void sing();
}
public class Plane implements Fly{
/**
* 飞机类
*/
@Override
public void fly() {
System.out.println("I'm a Plane and I can fly!");
}
}
public class Bird implements Fly,Sing{
/**
* 鸟类
*/
@Override
public void fly() {
System.out.println("I'm a Bird and I can fly too!");
}
@Override
public void sing() {
System.out.println("I'm a Bird and I can sing!");
}
@Override
public void think() {
System.out.println("I'm a Bird. Somebody asks me why could I sing. Because I can Think!");
}
}
public class YoungBird extends Bird implements Fly,Sing{
public void sing(){
System.out.println("I'm a Young bird and I can sing just like my father!");
}
public void fly(){
System.out.println("I'm a Young bird and I can fly just like my father!");
}
public void think(){
System.out.println("I'm a Young Bird. Somebody asks me why could I sing. Because I can Think just like my father!");
}
}
public class Test2 {
/**
* 测试类
*/
public static void main(String[] args) {
Fly f = new Plane();
Fly f2 = new Bird();
Sing f3 =new Bird();
Think f4 = new Bird();
Fly f5 = new YoungBird();
Sing f6 =new YoungBird();
Think f7 = new YoungBird();
f.fly();
f2.fly();
f3.sing();
f4.think();
f5.fly();
f6.sing();
f7.think();
}
}}
控制台输出:
I'm a Plane and I can fly!
I'm a Bird and I can fly too!
I'm a Bird and I can sing!
I'm a Bird. Somebody asks me why could I sing. Because I can Think!
I'm a Young bird and I can fly just like my father!
I'm a Young bird and I can sing just like my father!
I'm a Young Bird. Somebody asks me why could I sing. Because I can Think just like my father!
5、抽象类与接口的区别总结
(1)抽象对象
抽象类:对事物抽象
接口:对行为抽象(规范标准)
(2)成员变量
抽象类:可以定义变量、常量
接口:只能定义常量
(3)成员方法
抽象类:可以定义具体方法、抽象方法
接口:只能定义抽象方法
(4)构造方法
抽象类:有构造方法
接口:没有构造方法