ArrayList for 和 forEach遍历分析

Java中ArrayList集合数据结构:数组

顺序存储,Random Access(Direct Access)这种方式,相邻的数据元素存放于相邻的内存地址中,整块内存地址是连续的,可以根据元素的位置直接计算出内存地址,直接进行读取。对于顺序存储读取一个特定位置元素的平均时间复杂度为O(1),遍历整个集合的平均时间复杂度为O(n)。正常来说,只有基于数组实现的集合,才有这种特性。

 

1.传统的for循环遍历,基于计数器的:

  遍历者自己在集合外部维护一个计数器,然后依次读取每一个位置的元素,当读取到一最后一个元素后停止。主要是需要按元素的位置来读取。这也是最原始的集合遍历方法。 

代码实现:

public static void forTest(List list){

    int size = list.size();

    for(int i=0;i

        String v =  list.get(i);

    }

}

 

反编译字节码:javap -c  xxx.calsss

ArrayList for 和 forEach遍历分析_第1张图片

 

源码分析:new ArrayList().get()

 

 public E get(int index) {
     rangeCheck(index);

   
return elementData(index);
}

 

E elementData(int index) {

    return (E) elementData[index];

}

从代码分析 ArrayList for遍历是通过数组下标获取数据

2.foreach 循环遍历:

屏蔽了显式声明的Iterator和计数器。内部也是采用了Iterator的方式实现,只不过Java编译器帮我们生成了这些代码

Iterator本来是OO的一个设计模式,主要目的是屏蔽不同数据集合的特点,统一遍历集合的接口。Java作为一个OO语言,自然也在Collections中支持了Iterator模式。相比于传统for循环,Iterator取缔了显式的遍历计数器。所以基于存储集合的Iterator可以直接按位置访问数据。

  优点:代码简洁,不易出错

  缺点:只能做简单的遍历,不能在遍历过程中(删除、替换)数据集合

 

代码实现:

 

public static void forEach(List list){

    for(String str : list){

       String v = str;

    }

}

 

反编译字节码:javap -c  xxx.calsss

ArrayList for 和 forEach遍历分析_第2张图片

 

 

源码解析:forEache实现new ArrayList().iterator().next()

 

public Iterator iterator() {

    return new Itr();

}

 

private class Itr implements Iterator {

    int cursor;       // index of next element to return

    int lastRet = -1; // index of last element returned; -1 if no such

    int expectedModCount = modCount;



    public boolean hasNext() {

        return cursor != size;

    }



    @SuppressWarnings("unchecked")

    public E next() {

        checkForComodification();

        int i = cursor;

        if (i >= size)

            throw new NoSuchElementException();

        Object[] elementData = ArrayList.this.elementData;

        if (i >= elementData.length)

            throw new ConcurrentModificationException();

        cursor = i + 1;

        return (E) elementData[lastRet = i];

    }



   //省略其他内部代码

}

 

从代码分析 ArrayList forEach遍历 是通过Iterator迭代器遍历数据,也是通过数组下标获取数据

 

ArrayList for、forEach 遍历测试结果如下:(测试结果仅供参考)

 

 

分析结果:整体来看性能差异不大,遍历次数越少 for 性能高于 forEach

遍历次数越多  forEach性能高于 for

 

你可能感兴趣的:(Java,基础篇,数据结构,java)