存在继承关系的Java类对象之间的类型转换(一)
类似于基本数据类型之间的强制类型转换。 方法一: 1. Child a = new Child(); 2. Parent b = a; 3. Child c = (Child) b; 该方法的步骤是: 1.创建1个子类对象 2.用超类引用该子类对象 3.另外1个子类引用将该超类引用强制的转换。 采用该方法的过程中:由于超类引用的是1个子类对象(引用的该子类对象的内存空间),因此该超类引用具备子类对象的特点,再将该超类引用强制转化为另外1个子类对象。 采用该方法可以实现对象类型由超类向子类的转化,并且在程序的编译和运行均不会出现异常。 方法二:(错误方法) 1.Parent b = new parent(); 2.Child c = (Child) b ; 采用该方法不能实现对象类型由超类向子类的转化,以上源程序编译正常,但是运行时会抛出class castException异常。 这是因为:可以执行类型转换“子=(子)父”,但需要运行时进行检查。如果父类变量引用的是正确的子类型(这句话的意思即为描述1中的内容:即父类对象要想造型转换后赋给子类对象,其本身引用的是子类型的内存空间),赋值将执行。如果父类变量引用的是不相关的子类型,将会生成class castException异常。
在java中,做强制类型转换时 解答: 说明以下几点: 对类进行类型转换的一般原则如下:
对象在继承关系中的改变 对象的赋值是地址标识的传递,即两个对象名共同使用同一段内存地址。在Java中,对父类与子类对象之间的赋值作了如下规定: 1、子类对象名可以赋值给父类对象名;但父类对象名不可以赋值给子类对象名。 即:父类对象名=子类对象名; 2、如果一个父类对象名已经被子类对象名所赋值,那可以将父类对象名经强制转换赋值给子类对象名。 即:子类对象名=(子类类名)父类对象名; 常用的一种形式:方法中形参用父类型,实参用子类的对象名.
总结:
1 //父类 2 class Parent 3 { 4 public static String kind="javastudy.extendsstudy.parent"; 5 public static int age=50; 6 public String name="Parent"; 7 8 //静态方法,返回包名 9 public static String getKind() 10 { 11 System.out.println("parent的getKind()方法被调用了"); 12 return kind; 13 } 14 15 //静态方法,返回年龄 16 public static int getAge() 17 { 18 System.out.println("Parent的getAge()方法被调用了"); 19 return age; 20 } 21 22 //实例方法,返回姓名 23 public String getName() 24 { 25 System.out.println("Parent的getName()方法被调用了"); 26 return this.name; 27 } 28 29 } 30 31 32 //子类 33 class Child extends Parent 34 { 35 public static String kind="javastudy.extendsstudy.child"; 36 public int age=25; 37 public String name="child"; 38 39 //隐藏父类静态方法 40 public static String getKind() 41 { 42 System.out.println("child的getkind()方法被调用了"); 43 return kind; 44 } 45 46 //获取父类包名 47 public static String getParentKind() 48 { 49 return Parent.kind; 50 } 51 52 //覆盖父类实例方法 53 public String getName() 54 { 55 System.out.println("child的getName()被调用了"); 56 return this.name; 57 } 58 59 //获取父类名称 60 public String getParentName() 61 { 62 return super.name; 63 } 64 /* 65 *错误,实例方法不能覆盖父类的静态方法 66 public int getAge() 67 { 68 return this.age; 69 } 70 */ 71 } 72 73 74 public class Tianyi 75 { 76 public static void main(String[] args) 77 { 78 Child child=new Child(); 79 //创建Child类对象child 80 81 Parent parent=child; 82 //用parent引用child对象 83 84 Child b = (Child) parent; 85 //将parent引用强制转换为Child对象child 86 87 System.out.printf("子类child名称:%s,年龄:%d,包名:%s%n",child.name,child.age,child.kind); 88 //输出:子类名称:child,年龄:25,包:javastudy.extendsstudy.child 89 90 System.out.printf("超类的名称:%s,年龄:%d,包名:%s%n",parent.name,parent.age,parent.kind); 91 //输出:转换后的名称:Parent,年龄:50,包:javastudy.extendsstudy.parent 92 93 System.out.printf("子类b名称:%s,年龄:%d,包名:%s%n",b.name,b.age,b.kind); 94 95 96 System.out.printf("子类child访问父类被隐藏的实例变量name:%s%n",child.getParentName()); 97 //输出:子类访问父类被隐藏的实例变量name:Parent 98 99 System.out.printf("子类b访问父类被隐藏的实例变量name:%s%n",b.getParentName()); 100 101 102 103 System.out.printf("子类child访问父类被隐藏的静态变量kind:%s%n",child.getParentKind()); 104 //输出:子类访问父类被隐藏的静态变量kind:javastudy.extendsstudy.parent 105 106 System.out.printf("子类b访问父类被隐藏的静态变量kind:%s%n",b.getParentKind()); 107 108 child.getName(); 109 //输出:child的getName()被调用了 110 111 b.getName(); 112 113 114 //**************注意看这个方法,返回的还是子类的getName 115 parent.getName(); 116 //输出:child的getName()被调用了 117 118 child.getKind(); 119 //输出:child的getkind()方法被调用了 120 121 b.getKind(); 122 123 parent.getKind(); 124 //输出:parent的getKind()方法被调用了 125 } 126 } 运行结果如下:
超类和子类均具备的实例方法getName,超类调用该函数时,被子类的的该函数覆盖了。
|