清除ArrayList的两个选项中哪一个更好更快,为什么?
list.clear()
或
list = new ArrayList<Integer>();
碰巧我必须随机清除我的ArrayList中的所有条目,我无法知道将来会有多少新条目,可能有0或1000.哪种方法更快更好,为什么?
答案 0 :(得分:71)
没有基准测试很难知道,但是如果你的ArrayList中有很多项目并且平均大小较低,那么创建一个新的ArrayList可能会更快。
http://www.docjar.com/html/api/java/util/ArrayList.java.html
public void clear() {
modCount++;
// Let gc do its work
for (int i = 0; i < size; i++)
elementData[i] = null;
size = 0;
}
答案 1 :(得分:23)
List.clear
会在不降低列表容量的情况下删除元素。
groovy:000> mylist = [1,2,3,4,5,6,7,8,9,10,11,12]
===> [1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12]
groovy:000> mylist.elementData.length
===> 12
groovy:000> mylist.elementData
===> [Ljava.lang.Object;@19d6af
groovy:000> mylist.clear()
===> null
groovy:000> mylist.elementData.length
===> 12
groovy:000> mylist.elementData
===> [Ljava.lang.Object;@19d6af
groovy:000> mylist = new ArrayList();
===> []
groovy:000> mylist.elementData
===> [Ljava.lang.Object;@2bfdff
groovy:000> mylist.elementData.length
===> 10
这里mylist被清除了,对它所持有的元素的引用被删除了,但它保留了相同的后备数组。然后mylist重新初始化并得到一个新的后备阵列,旧的得到了GCed。因此,一种方式保留在内存中,另一种方式抛出其内存并从头开始重新分配(使用默认容量)。哪个更好取决于您是否要减少垃圾收集流失或最小化当前未使用的内存量。列表是否足够长以便移出伊甸园可能是决定哪个更快的一个因素(因为这可能使垃圾收集更加昂贵)。
答案 2 :(得分:16)
我认为答案是它取决于一系列因素,例如:
这使得很难预测哪个更好。但我的直觉是差异不会那么大。
关于优化的两点建议:
不要浪费时间尝试对此进行优化...除非应用客观太慢 AND 使用profiler 告诉您这是一个性能热点。 (很可能其中一个先决条件不是真的。)
如果你决定优化它,那就科学地做。尝试两种(所有)备选方案,并通过在实际问题/工作负载/输入集上测量实际应用程序的性能来确定哪种方案最佳。 (由于我之前列出的因素,人工基准可能会给你答案,不能预测现实世界的行为。)
答案 3 :(得分:14)
第一个.clear();
将保持相同的列表清除列表。
第二个new ArrayList<Integer>();
在内存中创建一个新的ArrayList
。
建议:首先是因为这就是设计目的。
答案 4 :(得分:5)
尝试以下方案,同时采用这种方法。 1.清除arraylist obj for循环 2.在for循环中创建新的Arraylist。
List al= new ArrayList();
for(int i=0;i<100;i++)
{
//List al= new ArrayList();
for(int j=0;j<10;j++)
{
al.add(Integer.parseInt("" +j+i));
//System.out.println("Obj val " +al.get(j));
}
//System.out.println("Hashcode : " + al.hashCode());
al.clear();
}
令我惊讶。内存分配没有太大变化。
使用新的Arraylist方法。
之前循环总可用内存:64,909 ::
循环后总可用内存:64,775 ::
采用明确方法,
之前循环总可用内存:64,909 :: 循环后总可用内存:64,765 ::
所以这说从内存利用率角度来看使用arraylist.clear没有太大区别。
答案 5 :(得分:4)
如果清单中包含尽可能多的元素,并且如果您不需要空闲内存,则清除列表是一个更好的选择。但我的猜测是,它可能并不重要。在检测到性能问题并确定其来源之前,请不要尝试进行优化。
答案 6 :(得分:2)
list.clear()
将保持相同的ArrayList但内存分配相同。 list = new ArrayList<int>();
将为您的ArrayList分配新内存。
最大的区别在于,当您需要更多空间时,ArrayLists将动态扩展。因此,如果您调用list.clear()
,您仍然可能会为可能不需要的ArrayList分配大量内存。
那说list.clear()
会更快,但如果内存匹配,你可能想要分配一个新的ArrayList。
答案 7 :(得分:1)
我建议使用list.clear()而不是分配新对象。当您调用“new”关键字时,您将在内存中创建更多空间。实际上,它并不重要。我想如果你知道列表有多大,那么创建一个新空间然后指定数组的大小可能是一个好主意。
事实是,除非你正在进行科学编程,否则它并不重要。在这种情况下,你需要学习C ++。