一 ArrayList
1. arraylist里面是通过数组实现的
- /**
- * The array buffer into which the elements of the ArrayList are stored.
- * The capacity of the ArrayList is the length of this array buffer.
- */
- private transient Object[] elementData;
- /**
- * The size of the ArrayList (the number of elements it contains).
- *
- * @serial
- */
- private int size;
2. arraylist初始化的时候可以指定大小,如果你知道大小,在创建的时候最好指定
- public ArrayList(int initialCapacity) {
- super();
- if (initialCapacity < 0)
- throw new IllegalArgumentException("Illegal Capacity: "+
- initialCapacity);
- this.elementData = new Object[initialCapacity];
- }
3. arraylist添加元素的时候,需要判断存放元素的数组是否需要扩容(扩容大小是原来大小的1/2+1)
- public boolean add(E e) {
- ensureCapacity(size + 1); // Increments modCount!!
- elementData[size++] = e;
- return true;
- }
- public void ensureCapacity(int minCapacity) {
- modCount++;
- int oldCapacity = elementData.length;
- if (minCapacity > oldCapacity) {
- Object oldData[] = elementData;
- int newCapacity = (oldCapacity * 3)/2 + 1;
- if (newCapacity < minCapacity)
- newCapacity = minCapacity;
- // minCapacity is usually close to size, so this is a win:
- elementData = Arrays.copyOf(elementData, newCapacity);
- }
- }
4. arraylist 在指定位置添加元素或者移除指定位置元素,需要移动比较多的数据
- public void add(int index, E element) {
- if (index > size || index < 0)
- throw new IndexOutOfBoundsException(
- "Index: "+index+", Size: "+size);
- ensureCapacity(size+1); // Increments modCount!!
- System.arraycopy(elementData, index, elementData, index + 1,
- size - index);
- elementData[index] = element;
- size++;
- }
- public E remove(int index) {
- RangeCheck(index);
- modCount++;
- E oldValue = (E) elementData[index];
- int numMoved = size - index - 1;
- if (numMoved > 0)
- System.arraycopy(elementData, index+1, elementData, index,
- numMoved);
- elementData[--size] = null; // Let gc do its work
- return oldValue;
- }
二. LinkedList
1. linkedlist是通过链表实现的,一个节点是一个对象,包含了自己前一个节点的和后一个节点的地址
- private transient Entry<E> header = new Entry<E>(null, null, null);
- private transient int size = 0;
- private static class Entry<E> {
- E element;
- Entry<E> next;
- Entry<E> previous;
- Entry(E element, Entry<E> next, Entry<E> previous) {
- this.element = element;
- this.next = next;
- this.previous = previous;
- }
- }
2. 添加元素是通过移动链表指针
- public boolean add(E e) {
- addBefore(e, header);
- return true;
- }
- private Entry<E> addBefore(E e, Entry<E> entry) {
- Entry<E> newEntry = new Entry<E>(e, entry, entry.previous);
- newEntry.previous.next = newEntry;
- newEntry.next.previous = newEntry;
- size++;
- modCount++;
- return newEntry;
- }
3. 删除元素也是通过移动指针,所以理论上linkedlist比arraylist更适合添加和删除操作(不需要判断是否需要扩容,不需要移动大批的元素)
- public boolean remove(Object o) {
- if (o==null) {
- for (Entry<E> e = header.next; e != header; e = e.next) {
- if (e.element==null) {
- remove(e);
- return true;
- }
- }
- } else {
- for (Entry<E> e = header.next; e != header; e = e.next) {
- if (o.equals(e.element)) {
- remove(e);
- return true;
- }
- }
- }
- return false;
- }
- private E remove(Entry<E> e) {
- if (e == header)
- throw new NoSuchElementException();
- E result = e.element;
- e.previous.next = e.next;
- e.next.previous = e.previous;
- e.next = e.previous = null;
- e.element = null;
- size--;
- modCount++;
- return result;
- }
4. 获取元素需要遍历链表,比arraylist要慢
- public E get(int index) {
- return entry(index).element;
- }
- private Entry<E> entry(int index) {
- if (index < 0 || index >= size)
- throw new IndexOutOfBoundsException("Index: "+index+
- ", Size: "+size);
- Entry<E> e = header;
- if (index < (size >> 1)) {//size 右移一位表示除以2,其实就是看从前遍历快还是从后遍历快
- for (int i = 0; i <= index; i++)
- e = e.next;
- } else {
- for (int i = size; i > index; i--)
- e = e.previous;
- }
- return e;
- }
5. linkedlist 迭代器,支持向前向后迭代,在迭代过程中移除元素。如果要遍历linkedlist,建议使用迭代器,因为如果使用get方法效率没迭代器高。(从get方法的源码可以看出)
- private class ListItr implements ListIterator<E> {
- private Entry<E> lastReturned = header;
- private Entry<E> next;
- private int nextIndex;
- private int expectedModCount = modCount;
- ListItr(int index) { //支持从指定位置开始迭代
- if (index < 0 || index > size)
- throw new IndexOutOfBoundsException("Index: "+index+
- ", Size: "+size);
- if (index < (size >> 1)) {
- next = header.next;
- for (nextIndex=0; nextIndex<index; nextIndex++)
- next = next.next;
- } else {
- next = header;
- for (nextIndex=size; nextIndex>index; nextIndex--)
- next = next.previous;
- }
- }
- public boolean hasNext() {//是否有下一个
- return nextIndex != size;
- }
- public E next() { //下一个
- checkForComodification();
- if (nextIndex == size)
- throw new NoSuchElementException();
- lastReturned = next;
- next = next.next;
- nextIndex++;
- return lastReturned.element;
- }
- public boolean hasPrevious() { //是否有前一个
- return nextIndex != 0;
- }
- public E previous() { //前一个
- if (nextIndex == 0)
- throw new NoSuchElementException();
- lastReturned = next = next.previous;
- nextIndex--;
- checkForComodification();
- return lastReturned.element;
- }
- public int nextIndex() {
- return nextIndex;
- }
- public int previousIndex() {
- return nextIndex-1;
- }
- public void remove() { //删除元素
- checkForComodification();
- Entry<E> lastNext = lastReturned.next;
- try {
- LinkedList.this.remove(lastReturned);
- } catch (NoSuchElementException e) {
- throw new IllegalStateException();
- }
- if (next==lastReturned)
- next = lastNext;
- else
- nextIndex--;
- lastReturned = header;
- expectedModCount++;
- }
- public void set(E e) {
- if (lastReturned == header)
- throw new IllegalStateException();
- checkForComodification();
- lastReturned.element = e;
- }
- public void add(E e) {
- checkForComodification();
- lastReturned = header;
- addBefore(e, next);
- nextIndex++;
- expectedModCount++;
- }
- final void checkForComodification() {
- if (modCount != expectedModCount)
- throw new ConcurrentModificationException();
- }
- }
相关推荐
总的来说,理解ArrayList和LinkedList的基本特性和应用场景,以及如何处理与之相关的安全性问题,是Java程序员必备的知识。通过深入学习和实践,可以更好地利用这些数据结构提升程序效率和质量。
ArrayList和LinkedList是java中两个常用的实现List接口的类,它们之间的性能比较是一个非常重要的知识点。 首先,让我们来了解ArrayList和LinkedList的实现原理。ArrayList是基于数组结构实现的,而LinkedList是...
总结:ArrayList 和 LinkedList 是 Java 中两个常用的集合类,它们的底层实现方式不同,ArrayList 是基于数组实现的,而 LinkedList 是基于链表实现的。理解它们的底层实现方式可以帮助我们更好地使用它们。
总结来说,理解`List`接口及其常用实现类如`ArrayList`和`LinkedList`的特性是Java开发中必不可少的知识点。正确选择和使用这些数据结构能够显著提高程序的效率和可读性。同时,根据具体需求,利用`LinkedList`实现...
本文将深入探讨在"JAVA核心知识点整理"中涉及的关键概念和技术。 一、Java基础 Java的基础知识包括语法、面向对象特性(封装、继承、多态)、异常处理、输入/输出流以及集合框架。了解基本类型、类、接口、包的概念...
"Java集合知识点汇总" Java集合是Java语言中的一种数据结构,用于存储和操作数据。Java集合的知识点汇总将会涵盖Java集合的基本概念、类型、实现、操作和注意事项等方面。 Java集合的基本概念 Java集合是Java语言...
扩容操作是ArrayList的一个重要知识点,它涉及到数组的复制和内存分配,这可能导致一定的性能开销。因此,在预知需要大量插入元素的情况下,可以通过设置初始容量或合理地使用ensureCapacity方法来避免频繁扩容。 ...
Java容器ArrayList知识点总结 Java容器ArrayList是Java集合框架中的一种常用的容器实现,它的底层实现是基于数组的。ArrayList具有访问元素效率高、查询快、插入、修改、删除元素慢等特点,与LinkedList相比,它...
下面将详细阐述ArrayList的相关知识点。 **一、ArrayList简介** ArrayList是一个继承自AbstractList并实现了Serializable接口的类,它通过数组来存储元素。由于基于数组,ArrayList支持随机访问,即通过索引快速...
以下将详细介绍标题和描述中涉及的数据结构常考知识点及其Java实现。 1. 线性表: 线性表是最基础的数据结构,包括数组和链表两种形式。在Java中,数组是最直接的线性表实现,可以直接声明并初始化。链表则通过节点...
"Java实训:知识点与实战演练" Java实训是指通过实践和演练来提高Java编程技能的过程。在这篇资源摘要中,我们将概括Java实训的知识点和实战演练,涵盖Java基础知识、面向对象编程、Java控制结构、Java异常处理、...
以上是对 Java 开发岗面试中常见知识点的详细解析,希望对你的面试准备有所帮助。在面试过程中,不仅要掌握理论知识,还要注重实际问题解决能力和项目经验的积累,这样才能在竞争激烈的 IT 行业中脱颖而出。
Java集合框架是Java中最重要的数据结构之一,包括ArrayList、LinkedList、HashSet、TreeSet等。面试中可能会问到集合框架的使用、实现原理等。 3. 高并发编程(JUC包) 高并发编程是Java开发中非常重要的一部分,...
这份"java知识点总结思维导图(xmind)"是为帮助学习者系统性地理解和掌握Java核心技术而精心整理的资料。思维导图作为一种有效的学习工具,能够帮助我们更好地组织和记忆信息,提高学习效率。 首先,让我们从基础...
以上内容仅是Java知识点的冰山一角,实际学习中还需要深入理解JVM原理、设计模式、反射、注解、模块化系统(如Java 9+的模块系统)以及现代开发工具如Maven、Gradle的使用。不断实践和项目经验积累,才能真正掌握...
Java 基础知识点 Java 是一种面向对象的编程语言,它具有抽象、继承、封装、多态性等特征。下面是 Java 基础知识点的详细解释: 1. 面向对象的特征: 面向对象编程的四个基本特征是抽象、继承、封装和多态性。 *...
这份名为"超详细的Java复习知识点2019——个人笔记"的文档,旨在为初学者提供一个全面且深入理解Java基础知识的指南。笔记内容可能涵盖了以下几个关键领域: 1. **Java语法基础**:包括变量、数据类型、运算符、...
1. **Java基础**:这是学习任何编程语言的基础,包括变量、数据类型、运算符、流程控制(如if/else,for,while)、类与对象、封装、继承、多态、接口、异常处理以及集合框架(如ArrayList,LinkedList,HashMap等)...
Java 基础知识点汇总 以下是 Java 基础知识点汇总的详细说明: ### 1. 面向对象的特征 面向对象编程(Object-Oriented Programming,OOP)是一种编程范式,它强调使用对象和类来组织和结构化代码。面向对象编程的...