java 通配符的使用-upcast

作者:无名 - 开源软件 -

package localevidence;
//: generics/UnboundedWildcards1.java
//: generics/CovariantArrays.java
class Fruit {}
class Appleee extends Fruit {}
class Jonathan extends Appleee {}
class Orange extends Fruit {}
public class Testwildcats {
public static void main(String[] args) {
Fruit[] fruit = new Appleee[10];
fruit[0] = new Appleee(); // OK
fruit[1] = new Jonathan(); // OK
// Runtime type is Appleee[], not Fruit[] or Orange[]:
try {
// Compiler allows you to add Fruit:
fruit[0] = new Fruit(); // ArrayStoreException
} catch(Exception e) { System.out.println(e); }
try {
// Compiler allows you to add Oranges:
fruit[0] = new Orange(); // ArrayStoreException
} catch(Exception e) { System.out.println(e); }
}
} /* Output:
java.lang.ArrayStoreException: Fruit
java.lang.ArrayStoreException: Orange
*///:~
Fruit[] fruit = new Appleee[10];// 这是实例化fruit数组为appleee类型

  但是编译没有错误,但是在runtime的时候为啥报错呢?

This makes sense to the compiler, because it has a Fruit[] reference—why shouldn’t it allow a Fruit 

object, or anything descended from Fruit, such as Orange, to be placed into the array So at compile time, this is allowed.

因为这对浏览器来说这是合理的,因为

Fruit[] fruit = new Appleee[10];
// Compiler allows you to add Fruit:
fruit[0] = new Fruit(); // ArrayStoreException

它有一个Fruit[]类型的申明,为啥不可以将Fruit 变量赋值给它呢,或者继承Fruit的子类呢?可以的编译器认为没有问题。

 The runtime array mechanism, however, knows that it’s dealing with an Apple [] and throws an exception when a foreign type is placed into the array.

但是runtime 运行机制却认为她是在处理Appleee[]类型的,所以如果你放入其它类型的就会报错。
"Upcast" is actually rather a misnomer here. What you’re really doing is assigning one array
to another.

"向上转型"事实上并不是不当,你实际在做的是将一种类型的数组赋值给另外一个数组。

 The array behavior is that it holds other objects, but because we are able to
upcast, it’s clear that the array objects can preserve the rules about the type of objects they
contain. It’s as if the arrays are conscious of what they are holding, so between the compile time checks and the runtime checks, you can’t abuse them.
This arrangement for arrays is not so terrible, because you do find out at run time that you’ve
inserted an improper type. But one of the primary goals of generics is to move such error
detection to compile time. So what happens when we try to use generic containers instead of
arrays

The real issue is that we are talking about the type of the container, rather than the type that
the container is holding.
The type of flist is now List< extends Fruit>, which you can read as "a list of any type
that’s inherited from Fruit." This doesn’t actually mean that the List will hold any type of
Fruit, however. The wildcard refers to a definite type, so it means "some specific type which
the flist reference doesn’t specify." So the List that’s assigned has to be holding some
specified type such as Fruit or Apple, but in order to upcast to flist, that type is a "don’t
actually care."

package localevidence;
public class Holder<T> {
	 private T value;
	 public Holder() {}
	 public Holder(T val) { value = val; }
	 public void set(T val) { value = val; }
	 public T get() { return value; }
	 public boolean equals(Object obj) {
	 return value.equals(obj);
	 }
	 public static void main(String[] args) {
	 Holder<Applee> Applee = new Holder<Applee>(new Applee());
	 Applee d = Applee.get();
	// Applee.set(d);
	 // Holder<Fruit> Fruit = Applee; // Cannot upcast
	 Holder< extends Fruit> fruit = Applee; // OK
	 Fruit p = fruit.get();
	 d = (Applee)fruit.get(); // Returns ‘Object’
	 try {
	 Orange c = (Orange)fruit.get(); // No warning
	 } catch(Exception e) { System.out.println(e); }
	 // fruit.set(new Applee()); // Cannot call set()
	 // fruit.set(new Fruit()); // Cannot call set()
	 System.out.println(fruit.equals(d)); // OK
	 }
	} /* Output: (Sample)
	java.lang.ClassCastException: Applee cannot be cast to Orange
	true
	*///:
//: generics/SuperTypeWildcards.java
import java.util.*;
public class SuperTypeWildcards {
static void writeTo(List< super Apple> apples) {
apples.add(new Apple());
apples.add(new Jonathan());
// apples.add(new Fruit()); // Error
}
} ///:~


本文内容由IT人知识库(原文链接:http://www.itpeo.net/15310/3488752.html)本站为各位整理





Extjs4 汉化

引入:ext-lang-zh_CN.js ext-lang-zh_CN.js<script ... ...

安装Tomcat6

1、安装JDK6.0 2、把下载的Tomcat6.0.29放于D:\Program Files\Apac... ...

PostgreSQL中将Integer类型的字段转换成Varchar类型的字段

rt,直接用pgadmin是没有办法进行这个转换的。 通过执行sql却是可以做到的,关键是添加USING... ...

rfedfre

剖析 Recipe

This topic provides an overview of the recipe framework,... ...

rfedfre

Cloudify安装与本地启动

1. Cloudify shell 1)JDK支持: 1.6以上版本; 环境变... ...

Qt学习系列4--使用线程

之前写qt程序的时候代码都是在一个gui线程中运行的,如果遇到一些比较耗时的操作会使界面失去响应,那么就需要把这些... ...

rfedfre

Qt学习系列3--Qt发布时遇到的问题(2014.08.26更新)

其实不必在环境变量里设置,使用qt.conf文件即可,qt5同样适用 参考:http://qt-project... ...

dedecms最新漏洞,可提权,20130713

截至当前时间2013年7月13日 该漏洞还未进行修复。 影响网站:   &n... ...

rfedfre

数据库水平切分的实现原理(分库,分表,主从,集群,负载均衡)

第1章  引言 随着互联网应用的广泛普及,海量数据的存储和访问成为了系统设计的瓶颈问题。对于一... ...

rfedfre

2015-05-12 python爬虫学习

开始学习python,在网上找了一个扒糗事百科精华的爬虫,自己稍许的修改了一下,就可以正常的扒拉糗百精华,别人的代... ...

rfedfre

学习spring必须java基础知识-注解(annotation)

有必要对JDK 5.0新增的注解(Annotation)技术进行简单的学习,因为Spring 支持@AspectJ... ...

准备把项目托管在开源中国的git上面【从IT eye上转的第一篇文章】

很久没写博客了,回归团队管理服务平台这个项目,我打算把这个项目托管在http://git.oschina.net... ...

Saltstack 自动化管理基础篇(一)

      Saltstack是一个新的基础设施管理工具。目前处... ...

rfedfre

学习Magento的路线

学习一门语言或者一个框架我们都可以按照一定的学习路线进行学习,这样可以节约时间,也可以提高学习的效率。以下是我在... ...

magento修改列表页每行商品显示数量

其实很简单,找到模板文件下list.phtml文件app\design\frontend\base\default... ...

ubuntu安装vsftpd

1.安装sudo apt-get install vsftpd 2.配置(具体网上搜) local_root... ...

windows系统下安装redis心得

在windows安装redis其实并没什么难度,而且网上攻略也很多。 起初,在安装好redis的时候,没有安装... ...

在MAC下安装redis以及其PHP扩展

Part1. 安装redis 命令不麻烦,在MacPorts的基础上进行安装。关于MacPorts的相关内容,... ...

fusionchart使用说明

data.xml 的格式可如下: <xml version="1.0" encoding="GBK... ...

获取当前位置并利用百度地图显示

根据百度提示的demo,将其manifest.xml中的内容参考而来: AndroidManifest.xml... ...