栏目分类:
子分类:
返回
名师互学网用户登录
快速导航关闭
当前搜索
当前分类
子分类
实用工具
热门搜索
名师互学网 > IT > 软件开发 > 后端开发 > Java

Object类和Comparable,clone接口

Java 更新时间: 发布时间: IT归档 最新发布 模块sitemap 名妆网 法律咨询 聚返吧 英语巴士网 伯小乐 网商动力

Object类和Comparable,clone接口

文章目录
  • Object类
    • Object类的好处
  • equals()方法
    • 重写equlas()方法
    • Object总结
  • JDK内置常用接口
    • Comparable接口
      • 重写compareTo()
    • Cloneable接口
      • 重写clone()方法
    • 深浅拷贝

Object类

object类是所有类的父类,无需使用extends来定义,声明的每个类都默认继承Object类.

Object类的好处
  • Object是所有类的父类,可以接受任意类型,是参数最高统一化.
   Object obj1 = new Dog();
   Object obj2 = "abc";
   Object obj3 = new int[10];
  • Object类的所有方法,子类都继承了.

为什么System类可以打印所有类型的数据,是因为Object里面有toString()方法.打印时会默认调用toString()方法.

	Animal dog = new Dog();
	System.out.println(dog);
	System.out.println(123);
	System.out.println("abc");

打印结果:

com.Dog@14ae5a5
123
abc

如果我们想输出对象中的属性值,那我们就在该对象中覆写toString()方法.

public class Dog {
    public String name="狗";
    public int age =20;
    
    @Override
    public String toString() {
       return "name"+name +","+ "age"+age;
    }
}

//Animal dog = new Dog();
//System.out.println(dog);
name狗,age20
equals()方法

如果我们要比较两个引用类型是否相等,我们使用equals()方法.

不能使用"=="比较,因为它比较的是地址.

	Student s1 = new Student();
	Student s2 = new Student();
	Student s3 = s1;
	System.out.println(s1==s2);//false
	System.out.println(s1==s3);//true
false
true

如果我们没有重写equals()方法,那运行时还是会默认调用Object中的equals()方法,Object中的equals()方法比较的还是地址,所以得到的结果和使用"=="相同.

	Student s1 = new Student();
	Student s2 = new Student();
	Student s3 = s1;
	System.out.println(s1.equals(s2));
	System.out.println(s1.equals(s3));
false
true

这是Object中的equals()方法.

重写equlas()方法

为什么要重写equals()方法?

如果我们不重写equals(),那么引用类型比较的是地址.如果我们想比较引用类型的成员变量呢,这时候就必须重写equals().

	Student s1 = new Student("小明",18);
	Student s2 = new Student("小华",20);
	Student s3 = new Student("小明",18);
	//我们要比较三个学生的成绩,我们就需要重写equals()方法
	System.out.println(s1.equals(s2));
	System.out.println(s1.equals(s3));

 //重写equals方法
    public boolean equals(Object obj) {
        //如果传入的是同一个对象
        if (this == obj) {
            return true;
        }
        //传入的变量不是同一对象
        if (obj instanceof Student) {
            //Object obj = new Student();
            //obj是Object类型,因为Object中没有成员变量name和age,所以必须向下转型
            Student stu = (Student) obj;
            // //这里的equal()方法调用的是String里面的,已经重写过了
            return this.age == stu.age && this.name.equals(stu.name);
        }
        return false;
    }

打印结果:

false
true
Object总结

什么时候会用到向下转型?

当一个Object类指向一个子类实例时,我们需要调用子类独有的属性和方法时,这时候就必须用到向下转型

我们要比较两个引用类型的什么属性,就在equals()里面重写.

Object可以接收各种引用类型,比如接口,数组,类等

但是Object 不能接收8大基本类型,所以包装类应运而生~~

JDK内置常用接口

接口优先原则:当一个场景即可以使用抽象类,又可以使用接口定义时,优先使用接口(更灵活).

Comparable接口

当一个类实现了Comparable接口,那么该类就具备了可比较的能力.

 public static void main(String[] args) {
        int[] data = new int[]{1,2,3};
        //调用sort进行排序
        Arrays.sort(data);
        System.out.println(Arrays.toString(data));


如果我们自定义一个类型.

  public static void main(String[] args) {
        Student[] s = new Student[]{
                new Student("小明", 80),
                new Student("小华", 90),
                new Student("小兰", 100)
        };
        //排序
        Arrays.sort(s);
        System.out.println(Arrays.toString(s));
    }
}


这是因为Student是一个自定义类型,对于编译器来说,它不像int一样大小一目了然,到底哪个Student大,哪个Student小,JDK无从得知,为了让Student具备可比较的能力,此时就必须让Student类中实现Comparable接口,覆写接口中的compareTo方法.

重写compareTo()

public class Student implements Comparable {
    public String name;
    public int score;

    public Student(String name, int score) {
        this.name = name;
        this.score = score;
    }

    @Override
    public String toString() {
        return name + ":" + score;
    }

    @Override
    public int compareTo(Object o) {
        if (this == o) {
            return 0;
        }
        if (o instanceof Student) {
            //o是Student对象
            //此时的o是Object类型,所以需要向下转型
            Student stu = (Student) o;
            //比较分数的大小
            return this.score - stu.score;
        }
        throw new IllegalArgumentException();
    }

    public static void main(String[] args) {
//        int[] data = new int[]{1,2,3};
//        //调用sort进行排序
//        Arrays.sort(data);
//        System.out.println(Arrays.toString(data));
        //s是一个Student类型的数组
        Student[] s = new Student[]{
                new Student("小华", 90),
                new Student("小明", 80),
                new Student("小兰", 100)
        };
        Arrays.sort(s);
        System.out.println(Arrays.toString(s));
    }

    public static void sort(Comparable[] arr) {
        for (int i = 0; i < arr.length - 1; i++) {
            for (int j = 0; j < arr.length - i - 1; j++) {
                if (arr[j].compareTo(arr[j + 1]) > 0) {
                    Comparable temp = null;
                    temp = arr[j];
                    arr[j] = arr[j + 1];
                    arr[j + 1] = temp;
                }
            }
        }
    }
}

Arrays.sort方法实际还是根据Comparable接口里面的compareTo方法的返回值进行比较的.

Cloneable接口

克隆接口:原对象和新对象是两个独立的个体,新对象是通过原对象拷贝而来的,属性值和原对象完全相同.

重写clone()方法

为了让一个类具有复制的能力,需要implements Cloneable接口,覆写clone()方法.

public class Animal implements Cloneable {
    public String name;

    public Animal(String name) {
        this.name = name;
    }

    @Override
    public Object clone() throws CloneNotSupportedException {
        Animal newAnimal = null;
        newAnimal = (Animal) super.clone();
        return newAnimal;
    }

    public static void main(String[] args) throws CloneNotSupportedException {
        Animal animal1 = new Animal("狗");
        //调用clone()克隆一个animal1
        Animal animal2 = (Animal) animal1.clone();
        //animal1和animal2为不同的对象
        System.out.println(animal1 == animal2);
        System.out.println(animal2.name);

		//如果我们再创建一个animal3,name="狗",那么这个animal2和animal3没有任何关系
		//只是恰好同名而已
		Animal animal3 = new Animal("狗");

    }
}

类似Comparable接口,这种接口被称为"标记"接口,这种接口内本身没有任何抽象方法,只有打上了这个标记的子类,才具备克隆的能力.

clone方法再克隆的时候不会调用无参构造方法.

  public Animal(){
        System.out.println("Animal的无参构造");
    }
	Animal animal1 = new Animal();
	Animal anima2 = animal1.clone();

深浅拷贝

转载请注明:文章转载自 www.mshxw.com
本文地址:https://www.mshxw.com/it/865411.html
我们一直用心在做
关于我们 文章归档 网站地图 联系我们

版权所有 (c)2021-2022 MSHXW.COM

ICP备案号:晋ICP备2021003244-6号