java 泛型--桥方法
因为 java 在编译源码时, 会进行 类型擦除, 导致泛型类型被替换限定类型(无限定类型就使用 Object
). 因此为保持继承和重载的多态特性, 编译器会生成 桥方法.
本文最后附录所有源码.
Pair
是个泛型类, 它具有泛型方法 setSecond(T second)
,
在经过编译时的 类型擦除 后变为 setSecond(Object second)
.
DateInterval
是 Pair<LocalDate>
的实例化子类, 它具有方法 setSecond(LocalDate second)
.
在 Main.main
中, 我们新建 DateInterval
对象, 并用基类 Pair<LocalDate>
来引用它,
此时调用基类的 setSecond
方法时, 我们希望它能够实现多态, 即调用 DateInterval.setSecond(LocalDate)
方法.
事实上, java 编译器通过插入 桥方法
的方式, 帮助我们实现了该功能.
反编译 DateInterval.class
会发现它具有两个 setSecond
方法:
void setSecond(LocalDate)
;void setSecond(Object)
.
并且, 在 void setSecond(Object)
中会调用 void setSecond(LocalDate)
, 这就是所谓的桥方法.
附: DateInterval.class
反编译后的代码:
Compiled from "DateInterval.java"
public class com.book.chapter8.DateInterval extends com.book.chapter8.Pair<java.time.LocalDate> {
public com.book.chapter8.DateInterval();
Code:
0: aload_0
1: invokespecial #1 // Method com/book/chapter8/Pair."<init>":()V
4: return
public void setSecond(java.time.LocalDate);
Code:
0: aload_1
1: aload_0
2: invokevirtual #2 // Method getFirst:()Ljava/lang/Object;
5: checkcast #3 // class java/time/chrono/ChronoLocalDate
8: invokevirtual #4 // Method java/time/LocalDate.compareTo:(Ljava/time/chrono/ChronoLocalDate;)I
11: iflt 19
14: aload_0
15: aload_1
16: invokespecial #5 // Method com/book/chapter8/Pair.setSecond:(Ljava/lang/Object;)V
19: return
public void setSecond(java.lang.Object);
Code:
0: aload_0
1: aload_1
2: checkcast #6 // class java/time/LocalDate
5: invokevirtual #7 // Method setSecond:(Ljava/time/LocalDate;)V
8: return
}
附: 其他所有源码:
Pair.java:
package com.book.chapter8;
/**
* Created by zhixiao.mzx on 2016/11/5.
*/
public class Pair<T> {
private T first;
private T second;
public Pair() {
first = null;
second = null;
}
public Pair(T first, T second) {
this.first = first;
this.second = second;
}
public T getFirst() {
return first;
}
public void setFirst(T first) {
this.first = first;
}
public T getSecond() {
return second;
}
public void setSecond(T second) {
this.second = second;
}
}
DateInterval.java:
package com.book.chapter8;
import java.time.LocalDate;
/**
* Created by zhixiao.mzx on 2016/11/5.
*/
public class DateInterval extends Pair<LocalDate> {
public void setSecond(LocalDate second) {
if (second.compareTo(getFirst()) >= 0) {
super.setSecond(second);
}
}
}
Main.java:
package com.book.chapter8;
import java.time.LocalDate;
/**
* Created by zhixiao.mzx on 2016/11/5.
*/
public class Main {
public static void main(String[] args) {
DateInterval interval = new DateInterval();
Pair<LocalDate> pair = interval;
pair.setFirst(LocalDate.now());
pair.setSecond(LocalDate.now());
}
}
java 泛型--桥方法的更多相关文章
- JAVA泛型使用方法总结
1. 基本概念: (1)什么是泛型? 泛型,即"参数化类型".即将类型由原来的具体的类型参数化,类似于方法中的变量参数,此时类型也定义成参数形式(可以称之为类型形参),然后在使用或 ...
- java泛型编译时被擦除引起多态的破坏,用 桥方法解决此类问题。(java 桥方法)
在JVM虚拟机中泛型编译的时候,会出现类型擦除.但是,在多态场景中,编译时,擦除方式会出现多态被破坏的可能. 举个栗子: A.java public class A<T> { void g ...
- java 泛型的类型擦除与桥方法
泛型类 --代码参考:java核心技术 卷1 第十版 public class Pair<T> { private T first; private T second; //构造器 pub ...
- java 泛型的类型擦除和桥方法
oracle原文地址:https://docs.oracle.com/javase/tutorial/java/generics/erasure.html 在Java中,泛型的引入是为了在编译时提供强 ...
- 0072 Java中的泛型--泛型是什么--泛型类--泛型方法--擦除--桥方法
什么是泛型,有什么用? 先运行下面的代码: public class Test { public static void main(String[] args) { Comparable c=new ...
- Java中的类型擦除与桥方法
类型擦除 Java在语法中虽然存在泛型的概念,但是在虚拟机中却没有泛型的概念,虚拟机中所有的类型都是普通类.无论何时定义一个泛型类型,编译后类型会被都被自动转换成一个相应的原始类型. 比如这个类 pu ...
- 使用java泛型设计通用方法
泛型是Java SE 1.5的新特性, 泛型的本质是参数化类型, 也就是说所操作的数据类型被指定为一个参数. 因此我们可以利用泛型和反射来设计一些通用方法. 现在有2张表, 一张user表和一张stu ...
- 初识Java泛型以及桥接方法
泛型的由来 在编写程序时,可能会有这样的需求:容器类,比如java中常见的list等.为了使容器可以保存多种类型的数据,需要编写多种容器类,每一个容器类中规定好了可以操作的数据类型.此时可能会有Int ...
- java泛型应用实例 - 自定义泛型类,方法
近 短时间需要使用泛型,就研究了下,发现网上的问关于泛型的文章都是讲原理的, 很少有提到那里用泛型比较合适, 本文就泛型类和泛型方法的使用给出两 个典型应用场景. 例如一个toString的泛型方法, ...
随机推荐
- redis实现简单延时队列(转)
继之前用rabbitMQ实现延时队列,Redis由于其自身的Zset数据结构,也同样可以实现延时的操作 Zset本质就是Set结构上加了个排序的功能,除了添加数据value之外,还提供另一属性scor ...
- Tasker 中文版(4.6u2)
http://www.anzhi.com/soft_1868913.html Tasker绝对称得上是Android系统的神器之一,与Auto Memory Manager不同,Tasker不是加速型 ...
- WICED™ <SMART> Software Development Kit
WICED™ Software Development Kit The WICED™ SDK includes the tools and software needed to create Wi-F ...
- 【php】利用php的构造函数与析构函数编写Mysql数据库查询类 (转)
上次在<[php]利用原生态的JavaScript Ajax为php进行MVC分层设计,兼容IE6>(点击打开链接) 一文中,对于php查询Mysql数据库的model.php写法还不够完 ...
- Ping用法大全
Ping是典型的网络工具.Ping可以辨别网络功能的某些状态. 这些网络功能的状态是日常网络故障诊断的基础.特别是Ping可以识别连接的二进制状态(也就是是否连通).可是,这仅仅是 ...
- C# 操作Excel大全
//引用Microsoft.Office.Interop.Excel.dll文件 //添加using using Microsoft.Office.Interop.Excel; using Excel ...
- JSP学习笔记(四):文件上传
JSP 可以与 HTML form 标签一起使用,来允许用户上传文件到服务器.上传的文件可以是文本文件或图像文件或任何文档.我们使用 Servlet 来处理文件上传,使用到的文件有: upload.j ...
- hdu 1007 Quoit Design(分治法求最近点对)
大致题意:给N个点,求最近点对的距离 d :输出:r = d/2. // Time 2093 ms; Memory 1812 K #include<iostream> #include&l ...
- ftm时钟源
FTMx_SC中的 CLKS时钟选择位 00 :无 01: System clock 10:Fixed frequency clock 11 External clock 此处的01:System c ...
- C# 怎么显示中文格式的星期几
1.DateTime.Now.ToString("dddd",new System.Globalization.CultureInfo("zh-cn")); 2 ...