首先,请先看一个简单的例子:
原来我对JAVA接口的用法:
interface A{
public abstract void b();
}
//B类执行A接口并实现抽象方法b()
public calss B implements A{
public void b(){
System.out.println("called";
}
//C类进行方法调用
pubic class C{
public C(){}
public call(){
public A a1 = new B(); 怪蜀黍
a1.b();
}
//省略main方法, new C.call();
}
代码大致是这种思想,也就是,用具体实现抽象方法的类来实例化接口类
-----------------------------
实现类 实现类对象=NEW 实现类();
实现类对象.实现类方法() ;
与
接口=new 实现类
接口。实现类方法()
都可能实现同样的功能
-------------------------------------------
Interface A {
abstract void f();
}
class B implements A{
void f(){
//body;
.......
.......
//body end
}
}
public calss c {
public static void main(String[] args){
B b = new B();
A a = (A)b;
a.f();
}
}
JAVA中 return的用法
我当时的问题是:
当A a = (A)b时,b发生了向上转型行为,故此时b被窄化,此时reference a 持有的对象应该只有其父接口中的函数有效,这是没有异议的,那么,当main中发生的调用
a.f()被执行时,真正唤起的函数式抽象函数f(),还是B中的f().
经过参阅资料和我自己的验证,得到的结论是:a.f()最终唤醒了B中的f();
通过思考和继续学习,我得到了如下的认识:
1、“向上转型”发生在编译期,子类被窄化后在型别上被视为其超类,窄化后在原子类中但不在其超类中的函数失效;但由其超类继承而来的接口依然可以被唤起。
2、子类向上转型后,其通过继承并覆写后的函数仍能被唤起,并能被准确识别及执行,即向上转型后的对象,其内有效的函数别调用时,能准确执行其自身未转型时的功能。
这个机制主要由java函数(非final函数)的“后期邦定”性质保障。
3、这个机制的优越处在于:当父类的一个接口函数被不同子类继承并覆写后,当个个子类通过向上转型时,只要唤醒父类接口,java虚拟机会自动准确的识别出究竟该调用那个具体的子类函数。
4、后期邦定依靠于执行期型别识别。这个概念我将于以后做出补充。
5、以上就是所谓的多态的一部分内容。
目前,我所了解到的多态带来的意义是:
开发变得容易些了,当很多不同的类要执行只有细小差别的功能的同名函数时,可以提供一个接口并暴露接口函数(那个细小差别函数的同名函数)作为公共接口函 数,其他不同的类可以继承并覆写那个接口,调用时,只需将这些类的对象向上转型,调用该接口即可,java机制会保证调用准确。这样做使得代码量减小,可 读性提高。
---------------------------------------------------
可以应用java中的上转型对象,实现java编程的多态。
上转型对象不是父类创建的对象,而是子类对象的“简化”状态,它不关心子类新增的功能,只关心子类继承和重写的功能。
当一个类有很多子类时,并且这些子类都重写了父类中的某个方法。
当使用上转型对象在调用这个方法时就可能具有多种形态。因为不同的子类在重写父类的方法时可能产生不同的行为。也就是说,不同对象的上转型对象调用同一方法可能产生不同的行为。
例如下面的程序你测试一下就可以理解这样的用法。
class Animal{
void cry(){}
}
class Dog extends Animal{
void cry(){
System.out.println("Wang!Wang!......");
}
}
class Cat extends Animal{
void cry(){
System.out.println("miao~~miao~~...");
}
}
public class Example5_9{
public static void main(String args[]){
Animal animal;
animal=new Dog(); //animal是Dog对象的上转型对象
animal.cry();
animal=new Cat(); //animal是Cat对象的上转型对象
animal.cry();
}
}
-------------------------------------------------------------
Java:接口回调与向上转型
1.接口回调是什么[2]?
接口回调是指:可以把使用实现了某一接口的类创建的对象的引用赋给该接口声明的接口变量,那么该接口变量就可以调用被类实现的接口的方法。实际上,当接口变量调用被类实现的接口中的方法时,就是通知相应的对象调用接口的方法,这一过程称为对象功能的接口回调。看下面示例.
interface People {
void peopleList();
}
class Student implements People {
public void peopleList() {
System.out.println("I’m a student.");
}
}
class Teacher implements People {
public void peopleList() {
System.out.println("I’m a teacher.");
}
}
public class Example {
public static void main(String args[]) {
People a; // 声明接口变量
a = new Student(); // 实例化,接口变量中存放对象的引用
a.peopleList(); // 接口回调
a = new Teacher(); // 实例化,接口变量中存放对象的引用
a.peopleList(); // 接口回调
}
}
结果:
I’m a student.
I’m a teacher.
再来看看向上转型(upcasting)的概念。
2.什么是向上转型[1]?
Shape s=new Circle();
这里,创建了一个Circle对象,并把得到的引用立即赋值给Shape。通过继承,Circle就是一种Shape。
假设你调用基类方法(它已在导出类中被覆盖):
s.draw();
由于后期绑定(多态),将会正确调用Circle.draw()方法。
3.Java中的跨类引用
在java里面,关于跨类引用,有两条规则应该记住:
1)如果a是类A的一个引用,那么,a可以指向类A的一个实例。或者说指向类A的一个子类,这是向上转型的情形。
2)如果a是接口A的一个引用,那么,a必须指向实现了接口A的一个类的实例。这是接口回调的情形。
在java里面,向上转型是自动进行的,但是向下转型却不是,需要我们自己定义强制进行.
class B extends A{}
public class A {
public static void main(String[] argts){
A a1=new A();
A a2=new B();//Upcasting
B b1=new B();
B b2=(B) new A();//DownCasting
}
}
4.向上转型与接口回调的区别
从实现了某接口的对象,得到对此接口的引用,与向上转型为这个对象的基类,实质上效果是一样的。这些对象都可以调用基类型提供的方法,对于接口来 说就是回调接口中的方法,对于父类来说就是调用父类的方法。当然在向上转型的情况下,还牵涉到子类重写(Override)父类方法的情形。
原来我对JAVA接口的用法:
interface A{
public abstract void b();
}
//B类执行A接口并实现抽象方法b()
public calss B implements A{
public void b(){
System.out.println("called";
}
//C类进行方法调用
pubic class C{
public C(){}
public call(){
public A a1 = new B(); 怪蜀黍
a1.b();
}
//省略main方法, new C.call();
}
代码大致是这种思想,也就是,用具体实现抽象方法的类来实例化接口类
-----------------------------
实现类 实现类对象=NEW 实现类();
实现类对象.实现类方法() ;
与
接口=new 实现类
接口。实现类方法()
都可能实现同样的功能
-------------------------------------------
Interface A {
abstract void f();
}
class B implements A{
void f(){
//body;
.......
.......
//body end
}
}
public calss c {
public static void main(String[] args){
B b = new B();
A a = (A)b;
a.f();
}
}
JAVA中 return的用法
我当时的问题是:
当A a = (A)b时,b发生了向上转型行为,故此时b被窄化,此时reference a 持有的对象应该只有其父接口中的函数有效,这是没有异议的,那么,当main中发生的调用
a.f()被执行时,真正唤起的函数式抽象函数f(),还是B中的f().
经过参阅资料和我自己的验证,得到的结论是:a.f()最终唤醒了B中的f();
通过思考和继续学习,我得到了如下的认识:
1、“向上转型”发生在编译期,子类被窄化后在型别上被视为其超类,窄化后在原子类中但不在其超类中的函数失效;但由其超类继承而来的接口依然可以被唤起。
2、子类向上转型后,其通过继承并覆写后的函数仍能被唤起,并能被准确识别及执行,即向上转型后的对象,其内有效的函数别调用时,能准确执行其自身未转型时的功能。
这个机制主要由java函数(非final函数)的“后期邦定”性质保障。
3、这个机制的优越处在于:当父类的一个接口函数被不同子类继承并覆写后,当个个子类通过向上转型时,只要唤醒父类接口,java虚拟机会自动准确的识别出究竟该调用那个具体的子类函数。
4、后期邦定依靠于执行期型别识别。这个概念我将于以后做出补充。
5、以上就是所谓的多态的一部分内容。
目前,我所了解到的多态带来的意义是:
开发变得容易些了,当很多不同的类要执行只有细小差别的功能的同名函数时,可以提供一个接口并暴露接口函数(那个细小差别函数的同名函数)作为公共接口函 数,其他不同的类可以继承并覆写那个接口,调用时,只需将这些类的对象向上转型,调用该接口即可,java机制会保证调用准确。这样做使得代码量减小,可 读性提高。
---------------------------------------------------
可以应用java中的上转型对象,实现java编程的多态。
上转型对象不是父类创建的对象,而是子类对象的“简化”状态,它不关心子类新增的功能,只关心子类继承和重写的功能。
当一个类有很多子类时,并且这些子类都重写了父类中的某个方法。
当使用上转型对象在调用这个方法时就可能具有多种形态。因为不同的子类在重写父类的方法时可能产生不同的行为。也就是说,不同对象的上转型对象调用同一方法可能产生不同的行为。
例如下面的程序你测试一下就可以理解这样的用法。
class Animal{
void cry(){}
}
class Dog extends Animal{
void cry(){
System.out.println("Wang!Wang!......");
}
}
class Cat extends Animal{
void cry(){
System.out.println("miao~~miao~~...");
}
}
public class Example5_9{
public static void main(String args[]){
Animal animal;
animal=new Dog(); //animal是Dog对象的上转型对象
animal.cry();
animal=new Cat(); //animal是Cat对象的上转型对象
animal.cry();
}
}
-------------------------------------------------------------
Java:接口回调与向上转型
1.接口回调是什么[2]?
接口回调是指:可以把使用实现了某一接口的类创建的对象的引用赋给该接口声明的接口变量,那么该接口变量就可以调用被类实现的接口的方法。实际上,当接口变量调用被类实现的接口中的方法时,就是通知相应的对象调用接口的方法,这一过程称为对象功能的接口回调。看下面示例.
interface People {
void peopleList();
}
class Student implements People {
public void peopleList() {
System.out.println("I’m a student.");
}
}
class Teacher implements People {
public void peopleList() {
System.out.println("I’m a teacher.");
}
}
public class Example {
public static void main(String args[]) {
People a; // 声明接口变量
a = new Student(); // 实例化,接口变量中存放对象的引用
a.peopleList(); // 接口回调
a = new Teacher(); // 实例化,接口变量中存放对象的引用
a.peopleList(); // 接口回调
}
}
结果:
I’m a student.
I’m a teacher.
再来看看向上转型(upcasting)的概念。
2.什么是向上转型[1]?
Shape s=new Circle();
这里,创建了一个Circle对象,并把得到的引用立即赋值给Shape。通过继承,Circle就是一种Shape。
假设你调用基类方法(它已在导出类中被覆盖):
s.draw();
由于后期绑定(多态),将会正确调用Circle.draw()方法。
3.Java中的跨类引用
在java里面,关于跨类引用,有两条规则应该记住:
1)如果a是类A的一个引用,那么,a可以指向类A的一个实例。或者说指向类A的一个子类,这是向上转型的情形。
2)如果a是接口A的一个引用,那么,a必须指向实现了接口A的一个类的实例。这是接口回调的情形。
在java里面,向上转型是自动进行的,但是向下转型却不是,需要我们自己定义强制进行.
class B extends A{}
public class A {
public static void main(String[] argts){
A a1=new A();
A a2=new B();//Upcasting
B b1=new B();
B b2=(B) new A();//DownCasting
}
}
4.向上转型与接口回调的区别
从实现了某接口的对象,得到对此接口的引用,与向上转型为这个对象的基类,实质上效果是一样的。这些对象都可以调用基类型提供的方法,对于接口来 说就是回调接口中的方法,对于父类来说就是调用父类的方法。当然在向上转型的情况下,还牵涉到子类重写(Override)父类方法的情形。