`

第十四章 类型信息2.0

 
阅读更多
类字面常量

Java 还提供了另一种方法来生成Class对象的引用:使用“类字面常量(class literal)”。对上述程序来说,看起来就象下面这样:

FancyToy.class;

这样做不仅更简单,而且更安全,因为它在编译期就会受到检查。并且它无需方法调用,所以也更高效。

类字面常量不仅可以应用于普通的类,也可以应用于接口、数组以及基本数据类型。以外,对于基本数据类型的包装类,还有一个标准域TYPE。TYPE域是一个引用,指向对应的基本数据类型的Class对象,如下所示:

boolean.class Boolean.TYPE 等

我建议使用”.class”的形式,以保持它们与常规类的一致性。

注意,有一点很有趣,当使用“.class”来创建对Class对象的引用时,不会自动地初始化该Class对象。为了使用类而作的准备工作实际包括三个步骤:

1. 加载,这是由类加载器执行的。该步骤将查找字节码,并从这些字节码中创建一个Class对象。

2. 链接。在链接阶段将验证类中的字节码,为静态域分配存储空间,并且如果必须的话,将解析这个类创建的对其他类的所有引用。

3. 初始化、如果该类具有超类,则对其初始化,执行静态初始化器和静态初始化快。

Class initable = Initable.class;
System.out.println(initable.staitcFinal);

初始化有效地实现了尽可能的“惰性”。从对initable引用的创建中可以看到,仅使用.class语法来获得对类的引用不会引发初始化。但是为了产生Class引用,Class.forName()立即就进行了初始化,就像在initable3引用的创建中所看到的。

如果一个static final值是“编译器常量”,就像Initable.staticFinal那样,那么这个值不需要对Initable类进行初始化就可以被读取。但是,如果只是将一个域设置为static和final的,还不足以确保这种行为,例如,对Initable.staticFinal2的访问将强制进行类的初始化,因为它不是一个编译器常量。

如果一个static域不是final的,那么在对它访问时,总是要求在它被读取之前,要先进行链接和初始化,就像在对Initable2.staticNonFinal的访问中所看到的那样。

泛化的Class引用

    Class引用总是指向某个Class对象,它可以制造类的实例,并包含可作用于这些实例的所有方法代码。它还包含该类的静态成员,因此,Class引用表示的就是它所指向的对象的确切类型,而该对象便是Class类的一个对象。

下面这两种语法都是正确的:
public static void main(String[] args) {
		Class intClass = int.class;
		Class<Integer> genericIntClass = int.class;
		genericIntClass = Integer.class;
		intClass = double.class;
		//genericIntClass = double.class  //illegal
}

如果你想稍微放松点限制,应该怎么办呢?乍一看,好像可以这样:

Class<Number> genericNumberClass = int.class

这看起来似乎是其作用的,因为Integer继承自Number。但是它无法工作,因为Integer Class对象不是Number Class对象的子类。

为了能在泛化的Class引用时放松限制,我使用了通配符,它是java泛型的一部分。通配符就是“?”,表示“任何事物”。因此,我们可以在上例的普通Class引用中添加通配符,并产生相同的结果:

public static void main(String[] args) {
Class<?> intClass = int.class;
intClass = double.class;
}

在java SE5中,Class<?>优于平凡的Class,即便它们是等价的,它表示你不是疏忽才这么做的。

为了创建一个Class引用,它被限定为某种类型,或该类型的任何子类型,你需要将通配符与extends关键字相结合,创建一个范围。因此,与仅仅声明Class<Number>不同们现在做如下声明:

public static void main(String[] args) {
Class<? extends Number> dounded = int.class;
dounded = double.class;
dounded = Number.class;
}

当你将泛型语法用于Class对象时,会发生一件很有趣的事情:newInstance()将返回该对象的确切类型,而不仅仅只是在ToyTest.java中看到的基本的Object。这在某种程度上有些限制:

public static void main(String[] args) {
		Class<FancyToy> ftClass = FancyToy.class;
		FancyToy fancyToy = ftClass.newInstance();
		Class<? super FancyToy> up = ftClass.getSuperclass();
		//this wont compile
		//Class<Toy> up2 = ftClass.getSuperclass();
		//Only produces Object;
		Object obj = up.newInstance();
	}

超类只能这样:Class<? super FancyToy> up = ftClass.getSuperclass();
不能:Class<Toy> up2 = ftClass.getSuperclass();
由于这种含糊性:up.newInstance()的返回值不是精确的类型,而是Object:
Object obj = up.newInstance();

新的转型语法
public static void main(String[] args) {
		Building b = new House();
		Class<House> houseType = House.class;
		House h = houseType.cast(b);
		h = (House)b;
	}

Case()方法接受参数对象,并将其转化为Class引用的类型。新的转型语法对于无法使用普通转型的情况显得非常有用。

分享到:
评论

相关推荐

    ASP.NET 2.0全程指南第14章

    第14章可能是关于特定主题的深入探讨,虽然具体的章节内容没有直接给出,但我们可以根据ASP.NET 2.0的核心特性来讨论一些可能涵盖的知识点。 1. **网站项目与Web应用项目**:ASP.NET 2.0引入了两种类型的项目模式...

    [ASP.NET.2.0.揭秘].Sams.ASP.NET.2.0.Unleashed.Jun.2006

     第14章 请求上下文  第15章 保护你的ASP.NET应用程序  第16章 Web Part让网站个性化  第17章 Ajax无刷新技术  第18章 性能与安全  第19章 调试与错误处理  第20章 打包与部署  第21章 学成出师——...

    Objective-C 2.0程序设计

    - **对象复制与归档**:第十八章和第十九章探讨了对象复制和归档的相关技术。复制允许创建对象的副本,而归档则是将对象序列化为可持久化的格式,以便将来恢复或在网络上传输。 #### 三、Cocoa和iPhone SDK - **...

    JSP2.0技术手册pdf(带示例源码).zip

    第十四章 JSP 与 JDBC 14-1 JDBC 简介 14-2 MySQL 的安装与使用 14-3 JDBC 连接 MySQL 14-4 JDBC 连接 MySQL 的中文问题 14-5 PreparedStatement 14-6 CallableStatement 14-7 JDBC 2.0 介绍与使用 14-8 JNDI - 数据...

    1.ASP.NET.2.0.XML.高级编程(第3版) [1/3]

    XML和ADO.NET\r\n第9章 显示XML数据 \r\n第10章 SQL Server 2005的XML集成 \r\n第11章 使用ASP.NET 2.0和SQL Server 2005构建飞机订票系统 \r\n第12章 XML串行化 \r\n第13章 XML Web服务\r\n第14章 ASP.NET 2.0配置 ...

    usb2.0技术规范中文版

    例如,外设厂家应重点关注第四章至第十章,而USB主机控制器应用则主要参考第四章至第七章和第九、十章。 #### 二、USB2.0的技术特点 ##### 2.1 设计目标 USB的设计目标主要是为了增强PC机的可扩展性、降低成本并...

    Webtop_2.0_Admin_Guide_1.1.pdf

    - **第14章:Webtop管理API**(页码305):介绍如何使用Netcool/Webtop管理API (WAAPI)工具,以及如何向Netcool/Webtop服务器发送XML配置指令。 - **附录A:HTML地图参考**(页码341):提供HTML地图命令语言的参考...

    ADO.NET 2.0技术内幕(高清 中文 带书签 全)

    第14章 生成高效的Web应用程序 14.1 Web应用程序简介 14.2 连接到数据库 14.3 在ASP.NET 1.0中与数据库进行交互时存在的问题 14.4 数据源控件简介 14.5 缓存往返的数据 14.6 分页 14.7 常见问题 第15章 SQL Server...

    usb2.0协议(word格式)

    主机控制器的实现主要关注第四至第七章和第九、十章,设备驱动程序开发则主要涉及第四、七、九章。配合其他相关文档,如《Universal Serial Bus Device Class Specification》,开发者可以全面了解USB 2.0 并开发出...

    USB2.0技术规范(中文).pdf

    主机控制器应用主要参考第四章至第七章和第九十章;USB设备驱动程序开发者主要参考第四、七、九章。 - **补充资料**:《Universal Serial Bus Device Class Specification》作为本书的补充材料,提供了更多关于特定...

    Django book 2.0 中文版

    14. **第十四章:会话、用户和注册** - Django 的认证系统详解。 - 用户会话的管理方法。 - 用户注册和登录流程的设计。 15. **第十五章:缓存机制** - Django 的缓存系统介绍。 - 不同类型的缓存存储选项。 ...

    Android2.0 游戏开发实战宝典

    在第14章,你会了解到如何使用SharedPreferences和SQLite数据库来保存游戏进度和用户设置。此外,还会讲解如何利用Android的Intent机制来实现游戏的启动、暂停和恢复。 网络功能在许多游戏中扮演着重要角色,第15...

    3.ASP.NET 2.0 入门经典(第4版) [压缩包1/10]

    第14章 性能 485 14.1 简单的技术 485 14.1.1 对象处理 486 14.1.2 数据库连接 489 14.1.3 存储过程 489 14.1.4 强类型的集合 498 14.1.5 会话状态 499 14.1.6 视图状态 499 14.2 页面和代码 500 14.2.1 ...

    零基础学ASP.NET 2.0电子书&源代码绝对完整版1

    示例描述:本章演示ASP.NET 2.0网站的预编译以及学习ASP.NET 2.0的前置知识。 WebSite文件夹 创建的ASP.NET 2.0 Web站点。 www文件夹 第一个用C#开发的Web应用程序。 bianyi.bat 编译网站的批处理文件。 ...

    ASP.NET 2.0+SQL Server 2005全程指南-源代码

    第14章 ASP.NET AJAX相关技术简介 14.1 Ajax概述 14.1.1 什么是Ajax 14.1.2 Ajax的工作原理 14.1.3 Ajax的优势与不足 14.2 ASP.NET AJAX 14.2.1 ASENET AJAX的特性 14.2.2 ASENET AJAX的安装 14.3 ASENET ...

    ASP.NET.2.0.编程-------珠玑

    第十四章专门讨论了安全方面的技巧,这对于任何.NET应用程序来说都是非常重要的。本章涵盖了如何防御SQL注入攻击等常见威胁,并提供了如何自定义Login控件以提高输入验证功能的方法。 #### 第15章:创建自己的窍门...

    UML2.0实战教程.pdf

    **第十一节:习题** 为了加深对面向对象的理解,本节提供了一系列习题供读者练习。 #### 第二章:UML入门 **第一节:UML的发展历史** - **起源**:UML(Unified Modeling Language,统一建模语言)是由Grady ...

Global site tag (gtag.js) - Google Analytics