黑马程序员——java基础之多态

——- android培训java培训、期待与您交流! ———-

一 多态

1. 多态的概念:
什么是多态:多态是同一个行为具有多个不同表现形式或形态的能力。可以理解为,事物存在的多中体现形态.
一个对象只有一个格式(是在构造时给它的)。但是,既然变量能指向不同格式的对象, 那么变量就是多态性的。也就是说一个对象只有一种形式,但一个变量却有多种不同形式。 象大多数面向对象语言一样,Java 实际上允许父类类型的引用变量指向一个子类的对象。

对象的多态性

人:男人 女人

动物:猫、狗

猫 x = new 猫();

动物 x = new 猫();

那么动物就是猫和狗具体事物中抽取出来的父类型。父类型引用指向了子类对象。

重载和覆盖是函数多态的体现

1 多态的基本体现
父类的应用指向了自己 的子类对象
父类的应用也可以接收机子的子类对象

2 多态的前提
必须是类与类之间有关系 要么继承 要么实现
通常还有一个前提 存在覆盖

3 多态的好处
多态的出现大大的提高了代码的拓展性

4 多态的特特点

5 多态的弊端
提高了拓展性 但是只能使用父类的引用访问父类中的成员

6 多态的出现代码中的特点(多态的注意事项)
—拓展性

想要调用猫的特有方法时,如何操作
向下转型 使用特有方法
强制将父类的 引用 转成子类类型

我们能转换的是父类的引用指向自己的子类对象时.该引用可以提升,也可以被强制转换

注意:不能将父类对象转成子类类型

多态自始至终都是子类对象在做变化

如下面的例子:

/*
    动物 猫狗
*/
//抽象出动物的共性--吃的特性
abstract class Animal
{
    abstract void eat();
}
//猫
class Cat extends Animal
{
    //复写父类的抽象方法
    public void eat()
    {
        System.out.println("吃鱼");
    }
    //定义自己的功能
    public void catchMouse()
    {
        System.out.println("抓老鼠");
    }
}
//定义狗
class Dog extends Animal
{
    public void eat()
    {
        System.out.println("吃骨头");
    }

    public void kanjia()
    {
        System.out.println("看家");
    }
}
//主类
class DT
{
    public static void main(String[] args)
    {
//      Cat c = new Cat();
//      Dog d = new Dog();

        //Animal a = new Cat();//类型提升  向上转型
        //a.eat();
        fun(new Cat());
        fun(new Dog());

        //想要调用猫的特有方法时,如何操作
        //向下转型 使用特有方法
        //强制将父类的!引用! 转成子类类型
        //Cat c = (Cat) a ;
        //c.catchMouse();   
    }
    public static void fun(Animal a)
    {
        a.eat();
        if(a instanceof Cat)
        {
            Cat c = (Cat)a;
            c.catchMouse();
        }
        if(a instanceof Dog)
        {
            Dog c = (Dog)a;
            c.kanjia();
        }   
    }
}

运行结果
这里写图片描述

————割———————————–割——————–

2. 多态的应用:

  1. 多态中,成员函数的特点
    在编译时:参阅引用型变量所属的类中是否有调用的方法,如果有,编译通过
    在运行时,参阅对象所属类中是否有调用的方法

总结就是:
成员函数在多态调用时 编译看左边 运行看右边

  1. 多态中,成员变量的特点
    无论编译和运行都参考左边(引用型变量所属的类)

  2. 在多态中,静态成员函数的特点
    无论编译和运行,都参考左边

下面来看一个多态的实际应用:
电脑的运行实例。电脑的运行由主板控制,
假设主板只是提供电脑运行,但是没有上网,听歌等功能。而上网、听歌需要硬件的支持。而现在主板上没有网卡和声卡,这时可以定义一个规则,叫PCI,只要符合这个规则的网卡和声卡都可以在主板上使用,
这样就降低了主板和网卡、声卡之间的耦合性。用程序体现。

/*
    需求:电脑运行示例
    电脑运行基于主板

*/
//用接口描述PCI规则
interface PCI
{
    public void open();
    public void close();

}
//主板
class MainBoard
{
    public void run()
    {
        System.out.println("Mainboard running");
    }
    //这里用到了多态的知识
    public void usePCI(PCI p)// PCI p = new NetCard();//接口型引用指向自己的子类对象
    {
        if(p!=null)
        {
            p.open();
            p.close();
        }
    }
}
//定义网卡
class NetCard implements PCI
{
    public void open()
    {
        System.out.println("netcard open");
    }
    public void close()
    {
        System.out.println("netcard close");
    }
}
//定义声卡
class SoundCard implements PCI
{
    public void open()
    {
        System.out.println("soundcard open");
    }
    public void close()
    {
        System.out.println("soundcard close");
    }

}
//主类
class MotherBoard
{
    public static void main(String[] args)
    {
        MainBoard mb = new MainBoard();
        mb.run();
        mb.usePCI(new NetCard());
        mb.usePCI(new SoundCard());

    }
}

运行结果
这里写图片描述

————割———————————–割——————–

二 equals 和 toString

Object 所有对像的直接或者间接父类 传说中的上帝
该类中定义的肯定是所有对象都具有的功能

Object 类中已经提供了对对像是否相同的比较方法

如果自定义类中也有比较相同的功能,建立自己特有比较内容即可, 这就是覆盖.

看下面的实例代码:

//每个类都默认继承Object类
class Demo//extends Object
{
    private int num;
    Demo (int num)
    {
        this.num = num;
    }
    //覆盖equals 方法
    public boolean equals(Object obj)//Object obj = new Demo()
    {
        if(!(obj instanceof Demo))
                return false;
            Demo d = (Demo) obj;
            return this.num==d.num;
    }
    //重写toString 方法
   public String toString()
    {
        return "Demo"+num;
    }

}

class ObjectDemo
{
    public static void main(String[] args)
    {
        Demo d1 = new Demo(5);
        Demo d2 = new Demo(5);
        System.out.println(d1.toString());//如果注释掉toString方法,那么这句的结果是Demo@1fb9ee3(hashCode)

        System.out.println(d1.equals(d2));//重写之后是内容相等才返回true. 因为如果没有重写,父类的equals比较的是两块内存是否一样,如果一样则返回true,否则为返回false.
}

运行结果:

这里写图片描述

——- android培训java培训、期待与您交流! ———-

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 1
    评论

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值