抽象类和接口的区别

当你改变想法的时候,记得也要改变你的世界。
——诺曼·文森特·皮尔

抽象类和接口的区别

两者的特点:

  • 抽象类用于描述类的共同特性和行为,可以有成员变量、构造方法和具体方法。适用于有明显继承关系的场景。
  • 接口用于定义行为规范,可以多实现,只能有常量和抽象方法(Java8 以后可以有默认方法和静态方法)。适用于定义类的能力或功能

两者的区别:

  • 实现方式:实现接口的关键字为implements,继承抽象类的关键字为extends。一个类可以实现多个接口,但一个类只能继承一个抽象类。所以,使用接口可以间接地实现多重继承。
  • 方法方式:接口只有定义,不能有方法的实现,java1.8中可以定义default方法体,而抽象类可以有定义与实现,方法可在抽象类中实现。
  • 访问修饰符:接口成员变量默认为public static final,必须赋初值,不能被修改;其所有的成员方法都是public、abstract的。抽象类中成员变量默认default,可在子类中被重新定义,也可被重新赋值;抽象方法被abstract修饰,不能被private、static、synchronized和native等修饰,必须以分号结尾,不带花括号。
  • 变量:抽象类可以包含实例变量和静态变量,而接口只能包含常量(即静态常量)

抽象类能加final修饰吗?

不能,Java中的抽象类是用来被继承的,而final修饰符用于禁止类被继承或方法被重写,因此抽象类和final修饰符是互斥的,不能同时使用。

抽象类可以被实例化吗?

在Java中,抽象类本身不能被实例化。

这意味着不能使用 new 关键字直接创建一个抽象类的对象。抽象类的存在主要是为了被继承,它通常包含一个或多个抽象方法(由 abstract 关键字修饰且无方法体的方法),这些方法需要在子类中被实现

抽象类可以有构造器,这些构造器在子类实例化时会被调用,以便进行必要的初始化工作。然而,这个过程并不是直接实例化抽象类,而是创建了子类的实例,间接地使用了抽象类的构造器。

public abstract class Abstractclass {
  	public Abstractclass(){
		// 构造器代码
    }

		public abstract void abstractMethod();
}


public class ConcreteClass extends AbstractClass {
  	public Concreteclass(){
				super();//调用抽象类的构造器
    }
  
	@Override
  public void abstractMethod(){
    // 实现抽象方法
  }
  
//下面的代码可以运行
ConcreteClass obj =new ConcreteClass();

在这个例子中,Concreteclass 继承了 Abstractclass 并实现了抽象方法 abstractMethod()。当我们创建Concreteclass 的实例时, Abstractclass 的构造器被调用,但这并不意味着Abstractclass 被实例化;实际上,我们创建的是 Concreteclass 的一个对象。
简而言之,抽象类不能直接实例化,但通过继承抽象类并实现所有抽象方法的子类是可以被实例化的。

接口里面可以定义哪些方法?

  • 抽象方法

    抽象方法是接口的核心部分,所有实现接口的类都必须实现这些方法。抽象方法默认是 public 和abstract,这些修饰符可以省略。

public interface Animal {
		void makeSound();
}

  • 默认方法

    默认方法是在 Java8 中引入的,允许接口提供具体实现。实现类可以选择重写默认方法。

public interface Animal {
		void makeSound();
  
		default void sleep(){
				System.out.printin("Sleeping...");
    }
}
  • 静态方法

    静态方法也是在 Java8中引入的,它们属于接口本身,可以通过接口名直接调用,而不需要实现类的对象。

public interface Animal {
		void makeSound();

		static void staticMethod(){
				System.out.println("Static method in interface");
    }
}
  • 私有方法

    私有方法是在 Java9 中引入的,用于在接口中为默认方法或其他私有方法提供辅助功能。这些方法不能被实现类访问,只能在接口内部使用。

public interface Animal{
		void makeSound();
  
		default void sleep(){
			System.out.printin("Sleeping...");
      logsleep();
    }
		private void logsleep(){
			System.out.printin("Logging sleep");
        }
}
posted @ 2025-03-28 10:07  Tsukinor  阅读(45)  评论(0)    收藏  举报