JAVA基础类库--Object

Object类用于统一对象、数组和接口。

Object类基本描述

1、Object类是所有类的父类,即任何一个类在没有定义继承某个类时,Object类就是其父类。

class Book{}	
class Book extends Object{}

上述两个类声明是等价的,Object类是唯一没有父类的类。Object类是所有类的父类,因此可以利用Object类通过向上转型,接收所有类型的对象。

class Book extends Object {
}

public class Demo {
    public static void main(String[] args) {
        Object objA = new Book(); // 向上转型
        Object objB = "Hello"; // 向上转型
        Book b = (Book) objA; // 向下转型
        String s = (String) objB; // 向下转型
    }
}

因此在不确定参数类型时,使用Object类型是最好的选择。
2、Object类中定义了一个无参构造方法,因为其是所有类的父类,所以实例化子类对象时必然会调用父类的无参构造方法。

一般而言,定义简单Java类时应覆写Object类中的如下方法:
· 取得对象信息:public String toString();
· 对象比较:public boolean equals(Object obj);
· 取得对象HASH码:public int hashCode();

toString()

class Book extends Object {
}

public class Demo {
    public static void main(String[] args) {
        Book b = new Book();
        String s = "Hello";
        System.out.println(b); // Book@1540e19d
        System.out.println(b.toString()); // Book@1540e19d
        System.out.println(s); // Hello
    }
}

上述代码中直接输出实例对象和使用toString()输出的结果是一样。因为输出对象时,会自动调用toString()将对象变为字符串后输出。Object类中的toString()为了适应对象的输出,仅输出对象的编码。
但是这和我们的想法不符,我们想输出的应该是实例化对象的属性信息,因此要覆写toString()。
范例:覆写toString()

class Book extends Object {
    private String title;
    private double price;

    // getter,setter,无参构造方法暂时略
    public Book(String title, double price) {
        this.title = title;
        this.price = price;
    }

    public String toString() {
        return "书名:" + this.title + ",价格:" + this.price;
    }
}

public class Demo {
    public static void main(String[] args) {
        Book b = new Book("Java开发", 20.3);
        System.out.println(b); // 书名:Java开发,价格:20.3
    }
}

此时直接输出对象,调用的就是覆写后的方法。

equals()

范例:对象比较

class Book extends Object {
    private String title;
    private double price;

    // getter,setter,无参构造方法暂时略
    public Book(String title, double price) {
        this.title = title;
        this.price = price;
    }

    public String toString() {
        return "书名:" + this.title + ",价格:" + this.price;
    }

    public boolean equals(Object obj) {
        if (this == obj) { // 地址相同
            return true;
        }
        if (obj == null) {
            return false;
        }
        if (!(obj instanceof Book)) { // 不是Book类对象
            return false;
        }
        Book book = (Book) obj;
        if (this.title.equals(book.title)
                && this.price == book.price) {
            return true;
        }
        return false;
    }
}

public class Demo {
    public static void main(String[] args) {
        Book bA = new Book("Java开发", 20.3);
        Book bB = new Book("Java开发", 20.3);
        System.out.println(bA.equals(bB)); // true
        System.out.println(bA.equals("Hello")); // false
    }
}

覆写后的equals()用于进行对象比较。

Object接收引用类型

1、Object类是所有类的父类,因此Object类对象可以接收所有类型的对象,包括数组和接口对象。
范例:接收数组数据

public class Demo {
    public static void main(String[] args) {
        Object obj = new int[]{1, 2, 3};
        System.out.println(obj); // [I@1540e19d表示数组
        if (obj instanceof int[]) { // 如果是数组,则输出
            int data[] = (int[]) obj; // 向下转型
            for (int x = 0; x < data.length; x++) {
                System.out.println(data[x]);
            }
        }
    }
}

范例:接收接口对象

interface A {
    public void fun();
}

class B implements A {
    public void fun() {
        System.out.println("Hello");
    }
}

public class Demo {
    public static void main(String[] args) {
        A a = new B();
        Object obj = a;
        A t = (A) obj;
        t.fun(); // Hello
    }
}

上述代码把参数类型统一为Object,有利于开发。

Object修改链表

此时我们可以利用Object类的特点解决之前开发的链表存在的问题:由于参数类型不统一,每次使用都要进行重新开发
范例:修改链表

class Link { // 链表类,外部可见
    private class Node { // 节点类
        private Object data; // 保存数据
        private Node next; // 引用关系

        public Node(Object data) { // 有数据才有Node
            this.data = data;
        }

        // 设置关系
        public void addNode(Node newNode) {
            if (this.next == null) {
                this.next = newNode;
            } else {
                this.next.addNode(newNode);
            }
        }

        // 数据查询
        public boolean containsNode(Object data) {
            if (data.equals(this.data)) { // 当前数据等于要目标数据
                return true; // 结束查询
            } else { // 当前数据不等于目标数据
                if (this.next != null) { // 有后续节点
                    return this.next.containsNode(data);
                } else { // 没有后续节点
                    return false;
                }
            }
        }


        public Object getNode(int index) {
            // 当前foot内容与要查询的索引比较
            // foot自增,目的是下次查询方便
            if (Link.this.foot++ == index) {
                return this.data;
            } else {
                return this.next.getNode(index);
            }
        }

        // 修改节点信息
        public void setNode(int index, Object data) {
            if (Link.this.foot++ == index) {
                this.data = data;
            } else {
                this.next.setNode(index, data);
            }
        }

        // 删除非根节点
        public void removeNode(Node previous, Object data) {
            // 参数中传递上一个节点和要删除的数据
            if (data.equals(this.data)) {
                previous.next = this.next;
            } else {
                this.next.removeNode(this, data);
            }
        }


        public void toArrayNode() {
            Link.this.retArray[Link.this.foot++] = this.data;
            if (this.next != null) {
                this.next.toArrayNode();
            }
        }
    }


    // ====================以上为内部类=====================
    private Node root; // 根节点
    private int count = 0; // 节点的个数
    private int foot = 0; // 索引
    private Object[] retArray; // 返回的数组

    public void add(Object data) {
        if (data == null) { // 输入数据为空
            return;
        }
        Node newNode = new Node(data); // 要保存的数据
        if (this.root == null) { // 根节点不存在
            this.root = newNode; // 设为根节点
        } else { //  根节点存在,交由Node处理
            this.root.addNode(newNode);
        }
        this.count++; // 每次增加节点,count+1
    }


    // 获取链表长度
    public int size() {
        return this.count;
    }

    // 判断是否为空链表
    public boolean isEmpty() {
        return this.count == 0;
    }


    // 判断数据是否存在
    public boolean contains(Object data) {
        if (data == null || root == null) {
            return false;
        }
        return this.root.containsNode(data);
    }

    // 根据索引获取信息
    public Object get(int index) {
        if (index > this.count) { // 超出查询范围
            return null;
        }
        this.foot = 0;
        return this.root.getNode(index); // 查询交给Node类
    }


    // 设置信息
    public void set(int index, Object data) {
        if (index > this.count) {
            return;
        }
        this.foot = 0; // 重置foot,作为索引
        this.root.setNode(index, data); // Node进行修改数据
    }

    // 判断删除节点是否为root
    public void remove(Object data) {
        if (this.contains(data)) { // 判断数据是否存在
            if (data.equals(this.root.data)) { // 判断数据是否是root数据
                this.root = this.root.next;
            } else {
                // root是Node对象,此处直接访问内部类私有操作
                this.root.next.removeNode(this.root, data);
            }
            this.count--; // 删除后数据个数减少
        }
    }

    public Object[] toArray() {
        if (this.root == null) {
            return null;
        }
        this.foot = 0; // 需要脚标控制
        this.retArray = new Object[this.count]; // 根据保存内容开辟数组
        this.root.toArrayNode();
        return this.retArray;
    }
}

范例: 测试程序

public class Demo {
    public static void main(String[] args) {
        Link all = new Link();
        all.add("A");
        all.add("B");
        all.add("C");
        System.out.println(all.size());
        all.remove("B");
        Object[] data = all.toArray();
        for (int x = 0; x < data.length; x++) {
            String str = (String) data[x];
            System.out.println(str);
        }
    }
}

综合实战: 宠物商店

要求: 以程序结构为主,实现一个宠物商店的模型,具有保存多个宠物的信息(名字,年龄),宠物上架、下架、模糊查询功能。
思路图
在这里插入图片描述

宠物商店的商品(宠物)要符合宠物这一标准(接口),宠物商店借助链表实现上架、下架和模糊查询功能。
范例:定义宠物的标准

interface Pet { // 定义宠物的标准
    public String getName();

    public int getAge();
}

宠物商店与具体的宠物无关,只和宠物这一接口有联系。
范例:定义宠物商店

class PetShop {
    private Link pets = new Link(); // 要保存的宠物信息

    public void add(Pet pet) { // 上架
        this.pets.add(pet);
    }

    public void delete(Pet pet) { // 下架
        this.pets.remove(pet);
    }

    public Link search(String keyWord) { // 模糊查询,返回的内容个数不明
        Link result = new Link();
        // 将集合以数组的形式返回,
        // 真正要查询的数据是Pet接口对象的getName()的返回值
        Object obj[] = this.pets.toArray();
        for (int x = 0; x < obj.length; x++) {
            Pet p = (Pet) obj[x];
            if (p.getName().contains(keyWord)) {
                result.add(p);
            }
        }
        return result;
    }
}

范例: 定义猫类

class Cat implements Pet {
    private String name;
    private int age;

    public Cat(String name, int age) {
        this.name = name;
        this.age = age;
    }


    public String getName() {
        return name;
    }

    public int getAge() {
        return age;
    }

    public boolean equals(Object obj) {
        if (this == obj) {
            return true;
        }
        if (obj == null) {
            return false;
        }

        if (!(obj instanceof Cat)) {
            return false;
        }
        Cat cat = (Cat) obj;
        if (this.name.equals(cat.name)
                && this.age == cat.age) {
            return true;
        }
        return false;
    }

    public String toString() {
        return "猫名:" + this.name + ", 年龄" + this.age;
    }
}

可参照上述结构,定义一个狗类。
范例:测试

public class Demo {
    public static void main(String[] args) {
        PetShop shop = new PetShop();
        shop.add(new Cat("阿猫", 9));
        shop.add(new Cat("猫咪", 19));
        shop.add(new Dog("阿狗", 10));
        shop.add(new Dog("狗子", 8));
        // 模糊查询
        Link all = shop.search("阿");
        Object obj[] = all.toArray();
        for (int x = 0; x < obj.length; x++) {
            System.out.println(obj[x]);
        }
        shop.delete(new Dog("狗子", 8));
    }
}
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值