文章目录

  • Lsit中数据复制问题
    • 1.1浅拷贝
    • 1.2深拷贝
    • 1.3 最终结论

Lsit中数据复制问题

这是由一道开放式面试题引发的文章,题目:加入内存足够大,一个集合中有100万条数据,怎么高效的把集合中的数据复制到另外一个集合

1.1浅拷贝

java 中复制分为浅拷贝和深拷贝

如果考察浅拷贝:直接使用clone方法

System.out.println("测试开始时");List<String> a=new ArrayList<String>(10000000);int i=1;for(int x = 1; x < 10000000; x = x+1){a.add(Integer.toString(x));}List<String> b=new ArrayList<String>(10000000);List<String> c=new ArrayList<String>(10000000);long begintime = System.nanoTime();b= (List<String>) ((ArrayList<String>) a).clone();  //浅拷贝

明显,问题没有这么简单

深度拷贝的话最简单就是遍历,这个基本都知道,自己实现遍历性能不会是最高的,开始思考
collections包含的方法

Collections.copy(c,a);

但这种方法具有局限,List c的size 要>= a.size()
并且根据代码这种方式也是浅拷贝

接下来想,如果是List
可以使用addall()
原理是数据拷贝,使用了java的native方法复制内存
同样也是浅拷贝

经过对比集中浅拷贝

java中提供了流式计算

 d = a.stream().collect(Collectors.toList());

经过实际验证:
addall()和collections.copy(a,b)
消耗时间接近,是比较好的复制方法,其中addall()略微好于collections

一般java的高效的集合类都在

java.util.concurrent.*;

分析代码:

long begintime5 = System.nanoTime();CopyOnWriteArrayList m=new CopyOnWriteArrayList(a);long endtime5 = System.nanoTime();long costTime5 = (endtime5 - begintime5)/1000;System.out.println("测试结束5: "+costTime5);

底层原理分析,看代码

 /*** Creates a list containing the elements of the specified* collection, in the order they are returned by the collection's* iterator.** @param c the collection of initially held elements* @throws NullPointerException if the specified collection is null*/public CopyOnWriteArrayList(Collection<? extends E> c) {Object[] elements;if (c.getClass() == CopyOnWriteArrayList.class)elements = ((CopyOnWriteArrayList<?>)c).getArray();else {elements = c.toArray();// c.toArray might (incorrectly) not return Object[] (see 6260652)if (elements.getClass() != Object[].class)elements = Arrays.copyOf(elements, elements.length, Object[].class);}setArray(elements);}

这段显示,调用了Arrays.copuOf()

/*** Copies the specified array, truncating or padding with nulls (if necessary)* so the copy has the specified length.  For all indices that are* valid in both the original array and the copy, the two arrays will* contain identical values.  For any indices that are valid in the* copy but not the original, the copy will contain <tt>null</tt>.* Such indices will exist if and only if the specified length* is greater than that of the original array.* The resulting array is of the class <tt>newType</tt>.** @param <U> the class of the objects in the original array* @param <T> the class of the objects in the returned array* @param original the array to be copied* @param newLength the length of the copy to be returned* @param newType the class of the copy to be returned* @return a copy of the original array, truncated or padded with nulls*     to obtain the specified length* @throws NegativeArraySizeException if <tt>newLength</tt> is negative* @throws NullPointerException if <tt>original</tt> is null* @throws ArrayStoreException if an element copied from*     <tt>original</tt> is not of a runtime type that can be stored in*     an array of class <tt>newType</tt>* @since 1.6*/public static <T,U> T[] copyOf(U[] original, int newLength, Class<? extends T[]> newType) {@SuppressWarnings("unchecked")T[] copy = ((Object)newType == (Object)Object[].class)? (T[]) new Object[newLength]: (T[]) Array.newInstance(newType.getComponentType(), newLength);System.arraycopy(original, 0, copy, 0,Math.min(original.length, newLength));return copy;}

接下来调用了

System.arraycopy(original, 0, copy, 0,
Math.min(original.length, newLength));

看看最后:

public static native void arraycopy(Object src,  int  srcPos,Object dest, int destPos,int length);

java的native 方法,效率最高
本质和collection的clone的方法逻辑一致

1.2深拷贝

集合的深度拷贝,除了遍历还有一种是序列化和反序列,这种首先排除在外,接下来看看还有没有其他方式

查询了资料,木有发现更好的深拷贝方法

经过实践对比,序列化、反序列化是效率最高的办法

1.3 最终结论

  public static <T> List<T> depCopy(List<T> srcList) {ByteArrayOutputStream byteOut = new ByteArrayOutputStream();try {ObjectOutputStream out = new ObjectOutputStream(byteOut);out.writeObject(srcList);ByteArrayInputStream byteIn = new ByteArrayInputStream(byteOut.toByteArray());ObjectInputStream inStream = new ObjectInputStream(byteIn);List<T> destList = (List<T>) inStream.readObject();return destList;} catch (IOException e) {e.printStackTrace();} catch (ClassNotFoundException e) {e.printStackTrace();}return null;}

以上针对问题,初步研究。

参考1:https://blog.csdn.net/u010648159/article/details/79144154
参考2:https://blog.csdn.net/demonliuhui/article/details/54572908

java集合数据复制到另外一个集合相关推荐

  1. 萌新的Python练习实例100例(七)将一个列表的数据复制到另一个列表中

    题目: 将一个列表的数据复制到另一个列表中 分析: · 这道题是联系list和切片的使用: 方法1: · 将b的值赋予a: · a[0:3]表示使用切片从0位置开始到第3位置结束: · a[:3]表示 ...

  2. Python-将一个列表的数据复制到另一个列表中

    # 题目:将一个列表的数据复制到另一个列表中 list1 = [x for x in range(1,5)]list2 = []print(list1)print(list2) #初始化 print( ...

  3. SQL语句 怎么把一个表的数据复制到另外一个表里面

    SQL语句 怎么把一个表的数据复制到另外一个表里面 SQL语句 怎么把一个表的数据复制到另外一个表里面   匿名 | 浏览 68087 次  我有更好的答案 推荐于2017-09-08 01:16:4 ...

  4. mysql复制一个字段值到另一个字段,MySQL怎么把表中一个字段数据复制到另外一个表的某个字段下...

    点击查看MySQL怎么把表中一个字段数据复制到另外一个表的某个字段下具体信息 答:update b set tel =(select mobile from a where a.id=b.aid) 注 ...

  5. SQL数据库中如何把一个表中的数据复制到另一个表中?

    SQL数据库中如何把一个表中的数据复制到另一个表中?** 1整个表复制:** insert into table1 select * from table2 2部分列复制:** insert into ...

  6. 把一个ListT的数据复制至另一个ListT

    把一个数据集List<T>复制至到另一个数据集List<T>. 方法一,可以使用循环,然后把每一个T添加至另一个集合中去: public void ListDemo(){var ...

  7. 英方软件:Data+引领数据复制的下一个十年

    点击上方关注我们! 接到英方软件新产品发布会的邀请才突然意识到,从2011正式成立到2020年,在我印象中那个始终意气风发.敢拼敢闯的英方软件,如今已经十岁了,并且在国内数据复制基础软件领域拥有了响当 ...

  8. oracle把一个表的数据复制到另一个表中

    1. 新增一个表,通过另一个表的结构和数据 create table XTHAME.tab1 as select * from DSKNOW.COMBDVERSION 2. 如果表存在: insert ...

  9. python判断数据是否在另一个集合中_python判断一个集合是否包含了另外一个集合中所有项的方法...

    {"moduleinfo":{"card_count":[{"count_phone":1,"count":1}],&q ...

最新文章

  1. MWC 2015:Peel全面升级为用户打造智能家居控制新体验
  2. cxf实现webservice
  3. 设置***遇到一个小问题
  4. boost::stacktrace模块实现终止处理程序的测试程序
  5. 如何从单个服务器扩展到百万用户的系统?
  6. 【Vegas原创】ASP 0131 不允许父路径的解决
  7. java学习(59):static修饰内部类
  8. sscanf解析复杂字符串,双引号通配符的使用问题
  9. idbconnection mysql_基于IDbConnection接口实现修改配置文件切换数据源
  10. python查看继承方法(一分钟读懂)
  11. 解析淘宝商城缘何更名“天猫”
  12. 【软件测试】白盒测试与黑盒测试的区别(不同)
  13. 本周论文推荐(12.14-12.20)
  14. python找到两个有序列表的中位数
  15. python初级爬虫工程师_如何入行爬虫工程师
  16. jspstudy启动mysql失败_mysql启动失败的一个解决方法
  17. python 读取pdf图片_Python如何读取pdf中的图片
  18. Sharepoint 列表关联Title字段设置
  19. AutoCAD Civil 3D 介绍
  20. 误删的文件怎么寻回?

热门文章

  1. 计算机无法联网错误代码105,错误代码105是什么意思?怎么办?
  2. 计算机软件系统存储和处理数据的基本单位是,计算机储存和处理数据的基本单位是什么...
  3. 十一大 WordPress 手机插件
  4. kubeedge设备添加以及mapper管理
  5. MikuMikuDance中对于Local和Global旋转方式的特殊处理
  6. 软件测试如何快速具备前端三剑客能力
  7. 《Day02》DIV+CSS样式,还不会排版优化自己网页?不是吧!不是吧!一看就会的东西
  8. 微博feed流nlp
  9. 微信,QQ抢红包算法(Java版)
  10. 十余家大数据及呼叫产业企业拟投资南明区