抽象类、密封类、接口

野性酷女 2022-04-22 08:38 380阅读 0赞

抽象类

  • 抽象类
    1.包含抽象方法的类,叫做抽象类。由abstract修饰。
    2.抽象类当中:可以有非抽象方法。
    3.抽象类不能创建实例对象。
  • 抽象方法
    1.在抽象类内部不给予实现。当有一个类,继承了当前的抽象类后,需要实现。
    2.抽象方法不能被private修饰,如果不加访问修饰限定符,默认为public。
  • 抽象类的派生类
    1.如果是普通类,那么必须实现抽象类的抽象方法。
    2.如果是抽象类,可以不实现基类的抽象方法。
  • 抽象类和普通类的区别
    1、抽象类不能被实例化。
    2、抽象方法不能被private修饰。
    3、抽象类被abstract修饰。
    4、抽象方法不能在抽象类当中实现。

如下代码为抽象类的例子:

  1. abstract class Animals {
  2. public abstract void bark();
  3. }
  4. //派生类为普通类,必须实现基类的抽象方法
  5. class Cat extends Animals {
  6. public void bark() {
  7. System.out.println("Cat:喵~~喵~~喵~~");
  8. }
  9. }
  10. class Dog extends Animals {
  11. public void bark() {
  12. System.out.println("Dog:汪~~汪~~汪~~");
  13. }
  14. }
  15. //派生类为抽象类,可以不实现基类的抽象方法
  16. abstract class Pig extends Animals {
  17. public void fun() {
  18. System.out.println("abstract class Pig:fun()");
  19. }
  20. }
  21. public class TestDemo5 {
  22. public static void main(String[] args) {
  23. Dog dog = new Dog();
  24. dog.bark();//Dog:汪~~汪~~汪~~
  25. Cat cat = new Cat();
  26. cat.bark();//Cat:喵~~喵~~喵~~
  27. }
  28. }

密封类

  • 密封类
    一个类被final修饰,称为密封类,为了防止有意的派生
  • 密封方法
    被final修饰的方法,不能被重写
  • 使用时应注意
    1.该类不能作为基类。
    2.派生类被final所修饰,该类也不可以作为基类。

如下代码为密封类的例子:

  1. final class Student {
  2. private String grade;
  3. private int id;
  4. private String name;
  5. public void setId(int id) {
  6. this.id = id;
  7. }
  8. public int getId() {
  9. return id;
  10. }
  11. }

接口

  • 接口

接口由interface定义
属性默认修饰符为public static final
方法默认修饰符为public abstract
如:

  1. interface One {
  2. public static final int COUNT = 1;//修饰符为默认的,只写int COUNT即可
  3. public abstract void methods1();
  4. }
  • 接口和抽象类的区别

1.接口内的方法,必须不能被实现,而抽象类可以存在非抽象方法。

2.抽象类只能继承一次,但是接口可以被实现或者继承多个。

a. 一个抽象类可以继承一个抽象父类,但是一个接口可以使用关键字
extends继承多个接口
b. 抽象类是对类整体的抽象 而接口是对行为(方法)进行抽象
c. 接口中的成员变量和成员方法默认为public static final
和public abstract
d. 抽象类当中的方法和成员变量的修饰符没有明确要求,但是抽象类当中的
方法不能用private修饰。

  1. interface One {
  2. public static final int COUNT = 1;
  3. public abstract void methods1();
  4. }
  5. interface Two {
  6. void methods2();
  7. }
  8. //这样写新的接口可以不实现extends后接口的方法
  9. interface Three extends One, Two {
  10. void methods3();
  11. }
  12. //实现接口Three
  13. class Test implements Three {
  14. public void methods1() {
  15. System.out.println("One.methods1()");
  16. }
  17. public void methods2() {
  18. System.out.println("Two.methods2()");
  19. }
  20. public void methods3() {
  21. System.out.println("Three.methods3()");
  22. }
  23. }
  24. public class TestDemo5 {
  25. public static void main(String[] args) {
  26. Test test = new Test();
  27. test.methods1();//One.methods1()
  28. test.methods2();//Two.methods2()
  29. test.methods3();//Three.methods3()
  30. One one = test;
  31. one.methods1();//One.methods1()
  32. Two two = test;
  33. two.methods2();//Two.methods2()
  34. Three three = test;
  35. three.methods3();//Three.methods3()
  36. }
  37. }
  • 三种接口

1.Comparator

在类外实现 int compare(T o1, T o2)方法

  1. class Teacher {
  2. private int id;
  3. private String subject;
  4. private String name;
  5. public Teacher(int id, String subject, String name) {
  6. this.id = id;
  7. this.subject = subject;
  8. this.name = name;
  9. }
  10. public int getId() {
  11. return id;
  12. }
  13. public void setId(int id) {
  14. this.id = id;
  15. }
  16. public String getName() {
  17. return name;
  18. }
  19. public void setName(String name) {
  20. this.name = name;
  21. }
  22. public String getSubject() {
  23. return subject;
  24. }
  25. public void setSubject(String subject) {
  26. this.subject = subject;
  27. }
  28. @Override
  29. public String toString() {
  30. return "Teacher{" +
  31. "id=" + id +
  32. ", subject='" + subject + '\'' +
  33. ", name='" + name + '\'' +
  34. '}';
  35. }
  36. }
  37. public class TestDemo4 {
  38. public static void main(String[] args) {
  39. Teacher[] teacher = new Teacher[3];
  40. teacher[0] = new Teacher(04, "History", "H.s");
  41. teacher[1] = new Teacher(02, "Math", "M.a");
  42. teacher[2] = new Teacher(03, "English", "E.n");
  43. System.out.println(Arrays.toString(teacher));
  44. System.out.println("========按姓名排序=========");
  45. Arrays.sort(teacher, new Comparator<Teacher>() {
  46. @Override
  47. public int compare(Teacher aa, Teacher bb) {
  48. return aa.getName().compareTo(bb.getName());
  49. }
  50. });
  51. System.out.println(Arrays.toString(teacher));
  52. System.out.println("========按id排序=========");
  53. Arrays.sort(teacher, new Comparator<Teacher>() {
  54. @Override
  55. public int compare(Teacher aa, Teacher bb) {
  56. return (aa.getId() - bb.getId());
  57. }
  58. });
  59. System.out.println(Arrays.toString(teacher));
  60. }
  61. }

输出结果:
在这里插入图片描述

2.Comparable

在类内实现compareTo(T o)方法

  1. class Teacher implements Comparable <Teacher>{
  2. private int id;
  3. private String subject;
  4. private String name;
  5. public Teacher(int id, String subject, String name) {
  6. this.id = id;
  7. this.subject = subject;
  8. this.name = name;
  9. }
  10. public int getId() {
  11. return id;
  12. }
  13. public void setId(int id) {
  14. this.id = id;
  15. }
  16. public String getName() {
  17. return name;
  18. }
  19. public void setName(String name) {
  20. this.name = name;
  21. }
  22. public String getSubject() {
  23. return subject;
  24. }
  25. public void setSubject(String subject) {
  26. this.subject = subject;
  27. }
  28. @Override
  29. public String toString() {
  30. return "Teacher{" +
  31. "id=" + id +
  32. ", subject='" + subject + '\'' +
  33. ", name='" + name + '\'' +
  34. '}';
  35. }
  36. @Override
  37. public int compareTo(Teacher aa) {
  38. return subject.compareTo(aa.subject);
  39. }
  40. }
  41. public class TestDemo4 {
  42. public static void main(String[] args) {
  43. Teacher[] teacher = new Teacher[3];
  44. teacher[0] = new Teacher(04, "History", "H.s");
  45. teacher[1] = new Teacher(02, "Math", "M.a");
  46. teacher[2] = new Teacher(03, "English", "E.n");
  47. Arrays.sort(teacher);
  48. System.out.println(Arrays.toString(teacher));
  49. }
  50. }

3.Clonable

  1. public interface Cloneable {
  2. }

此接口在源代码中为空接口,空接口的作用是标记这个类可以进行clone,如果不实现这个接口JVM不能够识别。

实例:

  1. class Color implements Cloneable {
  2. String name;
  3. @Override
  4. protected Object clone() throws CloneNotSupportedException {
  5. return super.clone();
  6. }
  7. }
  8. class Size implements Cloneable {
  9. Color color;
  10. public Size() {
  11. this.color = new Color();
  12. }
  13. //重写Object的克隆方法
  14. @Override
  15. protected Object clone() throws CloneNotSupportedException {
  16. Size size = (Size) super.clone();
  17. size.color = (Color) this.color.clone();
  18. return size;
  19. }
  20. }
  21. public class TestDemo4 {
  22. public static void main(String[] args) throws CloneNotSupportedException {
  23. Size size = new Size();
  24. Size size1 = (Size) size.clone();
  25. System.out.println(size.color.name);
  26. System.out.println(size1.color.name);
  27. size1.color.name = "red";
  28. System.out.println(size.color.name);
  29. System.out.println(size1.color.name);
  30. }
  31. }

这种clone方法为深拷贝,原因如下:

在重写的clone()方法中有以下两条语句:
Size size = (Size) super.clone();
size.color = (Color) this.color.clone();

在例子中的代码中,第一条语句将size中的元素全部克隆到了size1中,但是Size类中只有指向Color的color,所以此时两者指向的地址相同

第二条语句将color指向的地址也同样复制了,所以size和size1中元素就会指向两个地址,即深拷贝,下面的图可以辅助理解
在这里插入图片描述

发表评论

表情:
评论列表 (有 0 条评论,380人围观)

还没有评论,来说两句吧...

相关阅读

    相关 抽象接口

    一、抽象类和接口的定义: 抽象类(abstract class): 使用abstract修饰符修饰的类。 实际点来说,一个抽象类不能实例化,因为“没有包含足够多的信息来描

    相关 抽象抽象方法、接口

    抽象方法:使用abstract修饰的方法,没有方法体,只有声明。 抽象类:包含抽象方法的类就是抽象类、通过抽象类,我们可以做到严格限制子类的设计,使子类之间更加通用 •使用

    相关 Kotlin密封

    Kotlin密封类 密封类被用于展示受限的类层次结构。当一个值可以有一个来自一个有限集合中的类型,但不能有任何其他类型。在某种程度上来说,它们是枚举类的扩展,一个枚举类型的