作者:困了电视剧
专栏:《JavaSE语法与底层详解》
文章分布:这是一篇关于抽象类和接口的文章,在本篇文章中我会介绍其相关的定义和语法,并且揭示接口和抽象类的运行逻辑,提高对面对象编程的理解。
目录
抽象类
抽象类概念及其语法
抽象类特性
抽象类作用
接口
接口的概念和语法
接口的特性
接口和上转型在项目中被使用的逻辑(核心)
类,抽象类,接口的比较
abstract class Animal{
int age;
String name;
String sex;
//构造方法
public Animal(int age, String name, String sex) {
this.age = age;
this.name = name;
this.sex = sex;
}
public Animal(){}
//抽象方法
public abstract void eat();
public abstract void speak();
//普通方法
public void sleep(){}
}
1. 抽象类不能直接实例化对象2. 抽象方法不能是 private 的3. 抽象方法不能被 final 和 static 修饰,因为抽象方法要被子类重写4. 抽象类必须被继承,并且继承后子类要重写父类中的抽象方法,否则子类也是抽象类,必 须要使用 abstract 修饰5. 抽象类中不一定包含抽象方法,但是有抽象方法的类一定是抽象类6. 抽象类中可以有构造方法,供子类创建对象时,初始化父类的成员变量
abstract class Animal{
int age;
String name;
String sex;
//构造方法
public Animal(int age, String name, String sex) {
this.age = age;
this.name = name;
this.sex = sex;
}
public Animal(){}
//抽象方法
public abstract void eat();
public abstract void speak();
//普通方法
private void sleep(){}
}
class Cat extends Animal{
@Override
public void eat() {
}
@Override
public void speak() {
}
@Override
public void sleep(){
System.out.println("aaaaaa");
}
}
这段代码会报错
4.由于抽象类并不能实例化对象,所以如果抽象类想要被使用的话就必须被继承,被继承到子类时也是抽象方法,所以如果子类不对其进行重写,则子类包含抽象方法,只能用抽象类来进行定义。
public interface Code {
public abstract void test1();
public abstract void test2();
}
interface Code_test1 extends Code{
public abstract void test3();
}
interface Code_test2 extends Code,Code_test1{
public abstract void test4();
}
class Test1 implements Code,Code_test1,Code_test2{
@Override
public void test1() {
}
@Override
public void test2() {
}
@Override
public void test3() {
}
@Override
public void test4() {
}
}
1. 接口类型是一种引用类型,但是不能直接 new 接口的对象2. 接口中每一个方法都是 public 的抽象方法 , 即接口中的方法会被隐式的指定为 public abstract (只能是public abstract,其他修饰符都会报错 )3. 接口中的方法是不能在接口中实现的,只能由实现接口的类来实现4. 重写接口中方法时,不能使用默认的访问权限5. 接口中可以含有变量,但是接口中的变量会被隐式的指定为 public static fifinal 变量6. 接口中不能有静态代码块和构造方法7. 接口虽然不是类,但是接口编译完成后字节码文件的后缀格式也是 .class8. 如果类没有实现接口中的所有的抽象方法,则类必须设置为抽象类9. jdk8 中:接口中还可以包含 default 方法。
解释:
1.原因与抽象类类似,都是旨在提高代码的安全性,并且保证逻辑上的自洽。
2. 第二点和第五点中方法和变量前面的修饰符可加可不加,也可不加完,但在实际的项目中为了保证代码的简洁和统一,一般什么都不加。
public interface Code {
int a=0;
final int b=0;
public final int c=0;
public abstract void test1();
public void test2();
}
interface Code_test1 extends Code{
abstract void test3();
}
interface Code_test2 extends Code,Code_test1{
void test4();
}
class Test1 implements Code,Code_test1,Code_test2{
@Override
public void test1() {
}
@Override
public void test2() {
}
@Override
public void test3() {
}
@Override
public void test4() {
}
}
3.第四点中不能使用默认的类型是因为重写要求重写后的方法的访问权限不能低于重写前的方法,而在接口中默认的访问权限是public。
4.第七点编译后如图:
可以看到后缀名也是.class。
接口的命名一般采用形容词性的单词。
我们来看一段代码:
public class Javabit_Code {
public static void main(String[] args) {
Animal cat=new Cat();
Animal bird=new Bird();
Action ac=new Action();
ac.eat(cat);
ac.eat(bird);
ac.speak(cat);
ac.speak(bird);
ac.fly(new Bird());
}
}
class Action{
public void eat(Animal animal){
animal.eat();
}
public void speak(Animal animal){
animal.speak();
}
public void fly(Iflying animal){
animal.fly();
}
}
interface Iflying{
void fly();
}
abstract class Animal{
int age;
String name;
String sex;
//构造方法
public Animal(int age, String name, String sex) {
this.age = age;
this.name = name;
this.sex = sex;
}
public Animal(){}
//抽象方法
public abstract void eat();
public abstract void speak();
//普通方法
public void sleep(){}
}
class Cat extends Animal{
@Override
public void eat() {
System.out.println("吃猫粮");
}
@Override
public void speak() {
System.out.println("喵喵叫");
}
}
class Bird extends Animal implements Iflying{
@Override
public void eat() {
System.out.println("吃鸟粮");
}
@Override
public void speak() {
System.out.println("叽叽喳喳");
}
@Override
public void fly(){
System.out.println("鸟在飞");
}
}
在Action这个类中,我需要完成一些行为 ,但是此时由于我又不知道具体哪一个动物会被当做参数传进来,所以这里展现了多态的思想。
对于上转型来说,它提供了一种兼容,在Action类中的eat方法中,我需要传一个Animal的参数,这时我就可以运用上转型来完成这一点。
对于接口来说,它也提供了一种兼容,但和上转型又有点区别,上转型是“猫是动物”的关系即“is-a”的关系,而接口更像是“have-a”的关系,在本例中,他是只要实现了Iflying接口的类,其所实例化的对象就能当成参数,换个角度想,实现了Iflying接口就说明这个类实例化的对象会飞,而Action中的fly方法则是,只要是会飞的都可以实现这个方法。所以接口一般也用形容词进行命名。
这就是其中的逻辑关系。
类就相当于一张盖楼用的图纸,我用这张图纸可以实例化一个楼。
抽象类就相当于没画完的图纸,这张图纸在某些地方,比如这栋楼的厕所建造时需要的信息没有画,只画了这个厕所要建在大致哪个位置,所以由于信息不全不能实例化一个楼。
接口,就相当于一套楼房大致框架的信息,你需要先把这些信息抄到一张图纸上,然后再在这张图纸上按照实际的需求进行补全,这样才能实例化一个大楼。
以上就是本篇文章的全部内容,如果对你有帮助还请三连,如有疏漏欢迎指正。