用一个简单的巫师3案例初步理解java多态中的向上(下)转型

前言

  先声明一下,写这篇文章的目的是为了记录个人学习心得,可能存在许多不足与谬误,有劳各位指出。


首先说明多态和接口的一些特点。

一、多态性

  所谓多态性,务实点概括就是父类的对象可以指向子类的引用。
格式为:
  父类名称 对象名=new 子类名称();

  接口名称 对象名=new 实现类名称();
  这是一种向上转型的写法,之后可以使用父类对象调用子类中的成员方法,但仅限于子类重写父类的情况,子类特有的方法不行。
  如果使用某子类特有方法,则父类对象要向下转型为原本的子类,在此之前要进行判断父类引用原本是否为该子类(可以通过a instanceof B判断,a为父类引用,B为子类)。

二、接口使用

  1.不能直接使用,必须有一个实现类
格式:
   public class 实现类名称 implements 接口名称{
           //…
   }
   2.接口实现类必须覆盖重写接口中所有抽象方法;去掉abstract关键字,加上方法体大括号
   3.创建实现类对象进行使用

三、代码文件

1.Sward.java

public interface Sward {
	//两个抽象方法:拔剑与收剑
	public abstract void out();
	public abstract void back();
}

  这是一个接口,表示所有类型的剑,定义两个抽象方法,分别代表拔剑与收剑两种行为。

2.SteelSward.java&SilverSward.java

//钢剑类,实现剑接口
public class SteelSward implements Sward{
	//重写拔剑,拔钢剑
	@Override
	public void out() {
		System.out.println("拔出钢剑;");
	}
	//重写收剑,收钢剑
	@Override
	public void back() {
		System.out.println("收起钢剑。");
	}
	//钢剑特性,斩杀人类、亚人类与一般动物
	public void killSteel() {
		System.out.println("杀了一队守卫与一只野狗;");
	}
}
//银剑类,实现剑接口
public class SilverSward implements Sward{	
	//重写拔剑,拔银剑
	@Override
	public void out() {
		System.out.println("拔出银剑;");
	}
	//重写收剑,收银剑
	@Override
	public void back() {
		System.out.println("收起银剑。");
	}
	//银剑特性,斩杀天球交会的怪物
	public void killSilver() {
		System.out.println("杀了几只食尸鬼和一只日间妖灵;");
	}
}

  钢剑类与银剑类,游戏中是巫师3的一大特色。实现了Sward接口,重写接口中的拔剑与收剑动作方法,并各自添加了自己的特性方法(钢剑惩恶,银剑除魔)。

3.Witcher.java

public class Witcher {

	public void fightBegin() {
		System.out.println("开始战斗!");
	}
	
	public void fightEnd() {
		System.out.println("结束战斗!");
	}
	
	public void useSward(Sward sward) {
		sward.out();//调用拔剑		
		//判断原类型
		if(sward instanceof SteelSward) {
			SteelSward steelSward=(SteelSward)sward;//向下转型成SteelSward
			steelSward.killSteel();//调用钢剑特性
		}else if(sward instanceof SilverSward) {
			SilverSward silverSward=(SilverSward)sward;//向下转型成SilverSward
			silverSward .killSilver();//调用银剑特性
		}
		sward.back();//调用收剑
	}
		
}

  Witcher类,是SteelSward类与SilverSward类的使用者。
  可以看到,在useSward(Sward sward)方法中传入的参数是Sward接口引用,但实际使用中传入的参数也可以是实现类引用。如果这么写的话,则隐藏了一次向上转型,参见之后的测试部分代码。
  传入的接口引用在函数体中判断类型,向下转型成具体实现类,进行其特有行为。

4.WitcherFight.java

public class WitcherFight {
	public static void main(String[] args) {
		
		Witcher geralt=new Witcher();	//创建猎魔人对象杰洛特
		
		geralt.fightBegin();	//对象杰洛特调用开始战斗方法
		
		Sward steelSward=new SteelSward();	//多态式写法,用接口剑类型引用指向实现类钢剑类对象
		geralt.useSward(steelSward);	//杰洛特使用钢剑
		
		SilverSward silverSward=new SilverSward();	//常规写法,使用时自动转换类型
		geralt.useSward(silverSward);	//杰洛特使用银剑(向上转型)
			 
		geralt.fightEnd();//对象杰洛特调用结束战斗方法
	}
}

  用于测试,模拟猎魔人的一场战斗。在这里插入图片描述


总结

成员方法的参数类型是接口类型,而使用时传入参数的是它的实现类(自动转换类型),这是向上转型的一种用法;
当要使用实现类特性方法时,将接口类型转回原本的实现类,这是向下转型的一种用法。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值