【Java SE】抽象类和接口(二)

简介: 【Java SE】抽象类和接口

🐳如何实现接口间的继承

1. //把IRunning,ISwimming,Iflying全部继承到IAction上
2. 
3. interface IAction extends IRunning,ISwimming,Iflying{
4. 
5. }
6. 
7. class Swan extends Animal implements IAction {
8. 
9. 
10. public Swan(String name) {
11. super(name);
12.     }
13. 
14. @Override
15. public void run() {
16.         System.out.println(name + "正在跑");
17. 
18.     }
19. 
20. @Override
21. public void swim() {
22.         System.out.println(name + "正在游泳");
23. 
24.     }
25. 
26. @Override
27. public void fly() {
28.         System.out.println(name + "正在飞");
29. 
30.     }
31. }
32. 
33. public class Test {
34. 
35. public static void main(String[] args) {
36.        Swan swan=new Swan("白白");
37.        swan.run();
38.        swan.swim();
39.        swan.fly();
40. 
41.     }
42. 
43. }

接口间的继承相当于把多个接口合并在一起。

🐳抽象类和接口的区别:

(1)抽象类可以有构造方法,接口中不能有构造方法。

(2)抽象类中可以有普通成员变量,接口中没有普通成员变量。

(3)抽象类中可以包含静态方法,接口中不能包含静态方法。

(4) 一个类可以实现多个接口,但只能继承一个抽象类。

(5)接口可以被多重实现,抽象类只能被单一继承。

(6)如果抽象类实现接口,则可以把接口中方法映射到抽象类中作为抽象方法而不必实现,而在抽象类的子类中实现接口中方法。

接口和抽象类的相同点:

(1) 都可以被继承。

(2) 都不能被实例化。

(3) 都可以包含方法声明。

(4) 派生类必须实现未实现的方法。

 

🐳何为Object类?

Object是Java默认提供的一个类。Java里面除了Object类,所有的类都是存在继承关系的。默认会继承Object父类。即所有类的对象都可以使用Object的引用进行接收。

 

1. public class Test2 {
2. public static void main(String[] args) {
3. 
4.         fun1(new A());
5.         fun1(new B());
6.     }
7. public static void fun1(Object object){
8.         System.out.println(object);
9.     }
10. }
11. 
12. 
13. class A{
14. 
15. }
16. class B{
17. 
18. }

🐳利用Object类获取对象信息

如果要打印对象中的内容,可以直接重写Object类中的toString()方法

1. class Animal{
2. protected String name;
3. 
4. public Animal(String name){
5. this.name=name;
6.     }
7. 
8. @Override
9. public String toString() {
10. return "Animal{" +
11. "name='" + name + '\'' +//可以修改
12. '}';
13.     }
14. }

🐳 利用Object类进行对象比较

在Java中,==进行比较时:
a.如果==左右两侧是基本类型变量,比较的是变量中值是否相同
b.如果==左右两侧是引用类型变量,比较的是引用变量地址是否相同
c.如果要比较对象中内容,必须
重写Object中的equals方法,因为equals方法默认也是按照地址比较的

1. //Object类中的equals方法
2. public boolean equals(Object obj) {
3. return (this == obj); // 使用引用中的地址直接来进行比较
4. }
5. 
6. public class Test {
7. public static void main(String[] args) {
8.         Cat cat1=new Cat("小白",5);
9.         Cat cat2=new Cat("小白",5);
10. int a=10;
11. int b=10;
12.         System.out.println(a==b);
13.         System.out.println(cat1==cat2);
14.         System.out.println(cat1.equals(cat2));
15. 
16.     }
17. }
18. 
19. class Cat{
20. private String name;
21. private int age;
22. public Cat(String name,int age){
23. this.name=name;
24. this.age=age;
25.     }
26. }

重写equals方法后,然后比较:

1. @Override
2. public boolean equals(Object o) {
3. if (this == o) return true;
4. if (o == null || getClass() != o.getClass()) return false;
5. Cat cat = (Cat) o;
6. return age == cat.age && name.equals(cat.name);
7.     }

结论:比较对象中内容是否相同的时候,一定要重写equals方法。

🐳hashcode方法

hashcode方法用来确定对象在内存中存储的位置是否相同

事实上hashCode() 在散列表中才有用,在其它情况下没用。在散列表中hashCode() 的作用是获取对象的散列码,进而确定该对象在散列表中的位置。

我们认为两个名字相同,年龄相同的对象,将存储在同一个位置,如果不重写hashcode()方法

1. public class Test {
2. public static void main(String[] args) {
3.         Cat cat1=new Cat("小白",5);
4.         Cat cat2=new Cat("小白",5);
5.         System.out.println(cat1.hashCode());
6.         System.out.println(cat2.hashCode());
7. 
8.     }
9. }
10. 
11. class Cat{
12. private String name;
13. private int age;
14. public Cat(String name,int age){
15. this.name=name;
16. this.age=age;
17.     }
18. 
19. 
20. }

注意事项:两个对象的hash值不一样

像重写equals方法一样,我们也可以重写hashcode()方法。此时我们再来看看。

1. import java.util.Objects;
2. 
3. public class Test {
4. public static void main(String[] args) {
5.         Cat cat1=new Cat("小白",5);
6.         Cat cat2=new Cat("小白",5);
7.         System.out.println(cat1.hashCode());
8.         System.out.println(cat2.hashCode());
9. 
10.     }
11. }
12. 
13. class Cat{
14. private String name;
15. private int age;
16. public Cat(String name,int age){
17. this.name=name;
18. this.age=age;
19.     }
20. @Override
21. public int hashCode() {
22. return Objects.hash(name, age);
23.     }
24. 
25. }

哈希值一样。

相关文章
|
8天前
|
Java
Java中的抽象类:深入了解抽象类的概念和用法
Java中的抽象类是一种不能实例化的特殊类,常作为其他类的父类模板,定义子类行为和属性。抽象类包含抽象方法(无实现)和非抽象方法。定义抽象类用`abstract`关键字,子类继承并实现抽象方法。抽象类适用于定义通用模板、复用代码和强制子类实现特定方法。优点是提供抽象模板和代码复用,缺点是限制继承灵活性和增加类复杂性。与接口相比,抽象类可包含成员变量和单继承。使用时注意设计合理的抽象类结构,谨慎使用抽象方法,并遵循命名规范。抽象类是提高代码质量的重要工具。
25 1
|
25天前
|
Java
【Java】一个简单的接口例子(帮助理解接口+多态)
【Java】一个简单的接口例子(帮助理解接口+多态)
16 0
|
4天前
|
安全 Java 编译器
接口之美,内部之妙:深入解析Java的接口与内部类
接口之美,内部之妙:深入解析Java的接口与内部类
23 0
接口之美,内部之妙:深入解析Java的接口与内部类
|
8天前
|
缓存 安全 Java
Java中函数式接口详解
Java 8引入函数式接口,支持函数式编程。这些接口有单一抽象方法,可与Lambda表达式结合,简化代码。常见函数式接口包括:`Function<T, R>`用于转换操作,`Predicate<T>`用于布尔判断,`Consumer<T>`用于消费输入,`Supplier<T>`用于无参生成结果。开发者也可自定义函数式接口。Lambda表达式使实现接口更简洁。注意异常处理和线程安全。函数式接口广泛应用于集合操作、并行编程和事件处理。提升代码可读性和效率,是现代Java开发的重要工具。
18 0
|
8天前
|
Java 关系型数据库 MySQL
大厂面试题详解:Java抽象类与接口的概念及区别
字节跳动大厂面试题详解:Java抽象类与接口的概念及区别
33 0
|
8天前
|
Java
Java中的多线程实现:使用Thread类与Runnable接口
【4月更文挑战第8天】本文将详细介绍Java中实现多线程的两种方法:使用Thread类和实现Runnable接口。我们将通过实例代码展示如何创建和管理线程,以及如何处理线程同步问题。最后,我们将比较这两种方法的优缺点,以帮助读者在实际开发中选择合适的多线程实现方式。
19 4
|
25天前
|
Java
【Java】Clonable 接口
【Java】Clonable 接口
11 1
|
26天前
|
Java C#
java中的接口
java中的接口
11 0
|
4月前
|
Java
Java抽象类和接口
Java抽象类和接口
36 0
|
6月前
|
Java API 定位技术
Java---抽象类和接口
Java---抽象类和接口