Java中toArray的用法探究(java数组与list转换)
转载原文地址:
http://blog.csdn.net/guopengzhang/article/details/5497875
一. Incident
import java.util.ArrayList;
import java.util.List;
public class Test {
public static void main(String[] args) {
List<String> list = new ArrayList<String>();
list.add("1");
list.add("2");
String[] tt =(String[]) list.toArray(new String[0]);
}
}
这段代码是没问题的,但我们看到String[] tt =(String[]) list.toArray(new String[0]) 中的参数很奇怪,然而去掉这个参数new String[0]却在运行时报错。。。
二. Root Cause Analysis
经研究发现toArray有两个方法:
public Object[] toArray() {
Object[] result = new Object[size];
System.arraycopy(elementData, 0, result, 0, size);
return result;
}
不带参数的toArray方法,是构造的一个Object数组,然后进行数据拷贝,此时进行转型就会产生ClassCastException,这也就是上述问题的root cause了。
public Object[] toArray(Object a[]) {
if (a.length < size)
a = (Object[])java.lang.reflect.Array.newInstance(a.getClass().getComponentType(), size); System.arraycopy(elementData, 0, a, 0, size);
if (a.length > size)
a[size] = null;
return a;
}
而带参数的toArray方法,则是根据参数数组的类型,构造了一个对应类型的,长度跟ArrayList的size一致的空数组,虽然方法本身还是以 Object数组的形式返回结果,不过由于构造数组使用的ComponentType跟需要转型的ComponentType一致,就不会产生转型异常。
三. Solutions
因此在使用toArray的时候可以参考以下三种方式
1. Long[] l = new Long[<total size>];
list.toArray(l);
2. Long[] l = (Long[]) list.toArray(new Long[0]);
3. Long[] a = new Long[<total size>];
Long[] l = (Long[]) list.toArray(a);
四.Further Consideration
该容器中的元素已经用泛型限制了,那里面的元素就应该被当作泛型类型的来看了,然而在目前的java中却不是的,当直接String[] tt =(String[]) list.toArray()时,运行报错。回想一下,应该是java中的强制类型转换只是针对单个对象的,想要偷懒,将整个数组转换成另外一种类型的数组是不行的,这和数组初始化时需要一个个来也是类似的。
以上From: http://hi.baidu.com/%B4%CB%D6%D0%D3%D0%D5%E6%B5%C0/blog/item/8add93ec812dc9deb31cb1b0.html
- import java.util.*;
- class testList{
- public static void main(String[] args){
- //List<Character> list = new ArrayList<Character>();
- String[] str = "a b c".split(" ");
- System.out.println("字符串数组str,长度为:" + str.length);
- for(String c : str)
- System.out.println(c);
- List<Integer> list = new ArrayList<Integer>();
- list.add(1);
- list.add(2);
- list.add(3);
- list.add(4);
- Iterator<Integer> it = list.iterator();
- System.out.println("整型List list");
- while(it.hasNext())
- {
- System.out.println(it.next());
- }
- //数组转换成List
- List<String> li = new ArrayList<String>();
- li = Arrays.asList(str);
- Iterator<String> its = li.iterator();
- System.out.println("数组str -> list:");
- while(its.hasNext())
- {
- System.out.println(its.next());
- }
- //List转换成数组
- Integer[] b = (Integer[])list.toArray(new Integer[0]);
- System.out.println("List list -> 数组b");
- for(Integer i : b)
- System.out.println(i);
- //数组的fill方法
- int[] a = new int[5];
- Arrays.fill(a,0);
- System.out.println("数组a被0填充");
- for(int i : a)
- System.out.println(i);
- }
- }
Java中toArray的用法探究(java数组与list转换)的更多相关文章
- java中this的用法?
2008-07-28 08:10cztx5479 | 分类:JAVA相关 | 浏览4533次 java中this的用法? import java.awt.*; import java.awt.even ...
- Java 中 synchronized的用法详解(四种用法)
Java语言的关键字,当它用来修饰一个方法或者一个代码块的时候,能够保证在同一时刻最多只有一个线程执行该段代码.本文给大家介绍java中 synchronized的用法,对本文感兴趣的朋友一起看看吧 ...
- 转:十八、java中this的用法
http://blog.csdn.net/liujun13579/article/details/7732443 我知道很多朋友都和我一样:在JAVA程序中似乎经常见到“this”,自己也偶尔用到它, ...
- java成神之——java中string的用法
java中String的用法 String基本用法 String分割 String拼接 String截取 String换行符和format格式化 String反转字符串和去除空白字符 String获取 ...
- java中stringBuilder的用法
java中stringBuilder的用法 String对象是不可改变的.每次使用 System.String类中的方法之一时,都要在内存中创建一个新的字符串对象,这就需要为该新对象分配新的空间.在需 ...
- 第一篇 网站基础知识 第4章 Java中Socket的用法
第4章 Java中Socket的用法 4.1 普通Socket的用法 Java中的网络通信是通过Socket实现的,Socket分为ServetSocket和Socket两大类,ServetSocke ...
- Java中的Socket用法
转发链接:https://www.cnblogs.com/zhanglei93/p/6217384.html (1)Java中的Socket用法 Java中的Socket分为普通的Socket和Nio ...
- Java中Synchronized的用法
原文:http://blog.csdn.net/luoweifu/article/details/46613015 作者:luoweifu 转载请标名出处 <编程思想之多线程与多进程(1)——以 ...
- java中synchronized的用法详解
记下来,很重要. Java语言的关键字,当它用来修饰一个方法或者一个代码块的时候,能够保证在同一时刻最多只有一个线程执行该段代码. 一.当两个并发线程访问同一个对象object中的这个synchron ...
随机推荐
- defer属性---->执行外部脚本
HTML4---->只有IE支持 不需要是外部脚本. HTML5---->主流都支持 defer 属性仅适用于外部脚本(只有在使用 src 属性时) 值 描述 defer 规定当页面已完成 ...
- TP复习15
## ThinkPHP 3.1.2 URL#讲师:赵桐正微博:http://weibo.com/zhaotongzheng 本节课大纲:一.URL规则 1.默认是区分大小写的 2.如果我们不想区分大小 ...
- TP复习4
<script> window.onload=function(){ if(<{$data.sex}>==0){ document.getElementsByName('sex ...
- 【SSH三大框架】Hibernate基础第二篇:编写HibernateUtil工具类优化性能
相对于上一篇中的代码编写HibernateUtil类以提高程序的执行速度 首先,仍然要写一个javabean(User.java): package cn.itcast.hibernate.domai ...
- 你真的会使用SQL Server的备份还原功能吗?之二:主要备份类型
假设在下面几个时间段中,一个数据库积累插入了如下数据: 1.完整数据库备份 故名思意,完整数据库备份包括完整的数据库信息.它包括数据库的数据文件和备份结尾的部份活动事务日志. 完整备份基本语法如下: ...
- 关于ASP.NET中Button的OnClientClick属性
Button有Click属性和OnClientClick属性,执行顺序上OnClientClick先执行,调用本地脚本,根据返回值确定是否执行Click. 当返回True则执行Click,当脚本错误或 ...
- Oracle中关于清除数据和释放表空间
一.表的重命名 flashback table test2 to before drop rename to test3;--[to test3]将表重命名 drop table test3 purg ...
- jq实现地址级联效果
(function ($) { $.fn.Address = function (options) { var defaults = { divid: "Address", cal ...
- 【优先队列】HDU 1873——看病找医生
来源:点击打开链接 看路径记录的BFS之前,再看一遍优先队列的用法. 优先队列的排序规则可以用运算符重载的方式完成,通常意义下,应该用friend bool operator <进行重载. #i ...
- Java 使用 Redis
安装 开始在 Java 中使用 Redis 前, 我们需要确保已经安装了 redis 服务及 Java redis 驱动,且你的机器上能正常使用 Java. Java的安装配置可以参考我们的 Ja ...