Java重要類詳解之ArrayList類

来源:https://www.cnblogs.com/kungfupanda/archive/2018/07/12/9297507.html
-Advertisement-
Play Games

https://blog.csdn.net/shengmingqijiquan/article/details/52634640 一.ArrayList概述 ArrayList 是一個數組隊列,相當於動態數組。與Java中的數組相比,它的容量能動態增長。它繼承於AbstractList,實現了Lis ...


 

https://blog.csdn.net/shengmingqijiquan/article/details/52634640

 

一.ArrayList概述

  • ArrayList 是一個數組隊列,相當於動態數組。與Java中的數組相比,它的容量能動態增長。它繼承於AbstractList,實現了List,RandomAccess[隨機訪問],Cloneable[可克隆], java.io.Serializable[序列化]這些介面。
  • ArrayList 繼承了AbstractList,實現了List。它是一個數組隊列,提供了相關的添加、刪除、修改、遍歷等功能。
  • ArrayList 實現了RandmoAccess介面,即提供了隨機訪問功能。RandmoAccess是java中用來被List實現,為List提供快速訪問功能的。在ArrayList中,我們即可以通過元素的序號快速獲取元素對象;這就是快速隨機訪問。稍後,我們會比較List的“快速隨機訪問”和“通過Iterator迭代器訪問”的效率。
  • ArrayList 實現了Cloneable介面,即覆蓋了函數clone(),能被克隆。
  • ArrayList 實現java.io.Serializable介面,這意味著ArrayList支持序列化,能通過序列化去傳輸。
  • 和Vector不同,ArrayList中的操作不是線程安全的。所以,建議在單線程中才使用ArrayList,而在多線程中可以選擇Vector或者CopyOnWriteArrayList。
PS:以上繼承關係可以表示為以下形式:

 

二.ArrayList之API  

 

1.ArrayList和Collection之間的關係

*實線代表直接繼承的父類,虛線代表實現的介面;

2.ArrayList類的API

  1.   <span style="font-family:Microsoft YaHei;">// Collection中定義的API
  2.   boolean             add(E object)//添加一個數組對象
  3.   boolean             addAll(Collection<? extends E> collection)//添加一個包含Collection的對象
  4.   void              clear()//清空
  5.   boolean             contains(Object object)//包含
  6.   boolean             containsAll(Collection<?> collection)
  7.   boolean             equals(Object object)//判等
  8.   int               hashCode()
  9.   boolean             isEmpty()//判空
  10.   Iterator<E>         iterator()
  11.   boolean             remove(Object object)//刪除
  12.   boolean             removeAll(Collection<?> collection)
  13.   boolean             retainAll(Collection<?> collection)
  14.   int               size()
  15.   <T> T[]             toArray(T[] array)
  16.   Object[]            toArray()
  17.   // AbstractCollection中定義的API
  18.   void              add(int location, E object)
  19.   boolean             addAll(int location, Collection<? extends E> collection)
  20.   E                get(int location)//獲取某個元素值
  21.   int               indexOf(Object object)
  22.   int               lastIndexOf(Object object)
  23.   ListIterator<E>     listIterator(int location)
  24.   ListIterator<E>     listIterator()
  25.   E                remove(int location)
  26.   E                set(int location, E object)
  27.   List<E>             subList(int start, int end)
  28.   // ArrayList新增的API
  29.   Object             clone()//
  30.   void              ensureCapacity(int minimumCapacity)//保證容量不小於元素個數
  31.   void              trimToSize()
  32.   void              removeRange(int fromIndex, int toIndex)
  33.   </span>

3.ArrayList的源碼解析

  1.   <span style="font-family:Microsoft YaHei;">package java.util;
  2.   public class ArrayList<E> extends AbstractList<E>
  3.           implements List<E>, RandomAccess, Cloneable, java.io.Serializable
  4.   {
  5.       // 序列版本號
  6.       private static final long serialVersionUID = 8683452581122892189L;
  7.       // 保存ArrayList中數據的數組
  8.       private transient Object[] elementData;
  9.       // ArrayList中實際數據的數量
  10.       private int size;
  11.       // ArrayList帶容量大小的構造函數。
  12.       public ArrayList(int initialCapacity) {
  13.           super();
  14.           if (initialCapacity < 0)
  15.               throw new IllegalArgumentException("Illegal Capacity: "+
  16.                                                  initialCapacity);
  17.           // 新建一個數組
  18.           this.elementData = new Object[initialCapacity];
  19.       }
  20.       // ArrayList構造函數。預設容量是10。
  21.       public ArrayList() {
  22.           this(10);
  23.       }
  24.       // 創建一個包含collection的ArrayList
  25.       public ArrayList(Collection<? extends E> c) {
  26.           elementData = c.toArray();
  27.           size = elementData.length;
  28.           // c.toArray might (incorrectly) not return Object[] (see 6260652)
  29.           if (elementData.getClass() != Object[].class)
  30.               elementData = Arrays.copyOf(elementData, size, Object[].class);
  31.       }
  32.       // 將當前容量值設為 =實際元素個數
  33.       public void trimToSize() {
  34.           modCount++;
  35.           int oldCapacity = elementData.length;
  36.           if (size < oldCapacity) {
  37.               elementData = Arrays.copyOf(elementData, size);
  38.           }
  39.       }
  40.       // 確定ArrarList的容量。
  41.       // 若ArrayList的容量不足以容納當前的全部元素,設置 新的容量=“(原始容量x3)/2 + 1”
  42.       public void ensureCapacity(int minCapacity) {
  43.           // 將“修改統計數”+1
  44.           modCount++;
  45.           int oldCapacity = elementData.length;
  46.           // 若當前容量不足以容納當前的元素個數,設置 新的容量=“(原始容量x3)/2 + 1”
  47.           if (minCapacity > oldCapacity) {
  48.               Object oldData[] = elementData;
  49.               int newCapacity = (oldCapacity * 3)/2 + 1;
  50.               if (newCapacity < minCapacity)
  51.                   newCapacity = minCapacity;
  52.               elementData = Arrays.copyOf(elementData, newCapacity);
  53.           }
  54.       }
  55.       // 添加元素e
  56.       public boolean add(E e) {
  57.           // 確定ArrayList的容量大小
  58.           ensureCapacity(size + 1);  // Increments modCount!!
  59.           // 添加e到ArrayList中
  60.           elementData[size++] = e;
  61.           return true;
  62.       }
  63.       // 返回ArrayList的實際大小
  64.       public int size() {
  65.           return size;
  66.       }
  67.       // 返回ArrayList是否包含Object(o)
  68.       public boolean contains(Object o) {
  69.           return indexOf(o) >= 0;
  70.       }
  71.       // 返回ArrayList是否為空
  72.       public boolean isEmpty() {
  73.           return size == 0;
  74.       }
  75.       // 正向查找,返回元素的索引值
  76.       public int indexOf(Object o) {
  77.           if (o == null) {
  78.               for (int i = 0; i < size; i++)
  79.               if (elementData[i]==null)
  80.                   return i;
  81.               } else {
  82.                   for (int i = 0; i < size; i++)
  83.                   if (o.equals(elementData[i]))
  84.                       return i;
  85.               }
  86.               return -1;
  87.           }
  88.           // 反向查找,返回元素的索引值
  89.           public int lastIndexOf(Object o) {
  90.           if (o == null) {
  91.               for (int i = size-1; i >= 0; i--)
  92.               if (elementData[i]==null)
  93.                   return i;
  94.           } else {
  95.               for (int i = size-1; i >= 0; i--)
  96.               if (o.equals(elementData[i]))
  97.                   return i;
  98.           }
  99.           return -1;
  100.       }
  101.       // 反向查找(從數組末尾向開始查找),返回元素(o)的索引值
  102.       public int lastIndexOf(Object o) {
  103.           if (o == null) {
  104.               for (int i = size-1; i >= 0; i--)
  105.               if (elementData[i]==null)
  106.                   return i;
  107.           } else {
  108.               for (int i = size-1; i >= 0; i--)
  109.               if (o.equals(elementData[i]))
  110.                   return i;
  111.           }
  112.           return -1;
  113.       }
  114.    
  115.       // 返回ArrayList的Object數組
  116.       public Object[] toArray() {
  117.           return Arrays.copyOf(elementData, size);
  118.       }
  119.       // 返回ArrayList的模板數組。所謂模板數組,即可以將T設為任意的數據類型
  120.       public <T> T[] toArray(T[] a) {
  121.           // 若數組a的大小 < ArrayList的元素個數;
  122.           // 則新建一個T[]數組,數組大小是“ArrayList的元素個數”,並將“ArrayList”全部拷貝到新數組中
  123.           if (a.length < size)
  124.               return (T[]) Arrays.copyOf(elementData, size, a.getClass());
  125.           // 若數組a的大小 >= ArrayList的元素個數;
  126.           // 則將ArrayList的全部元素都拷貝到數組a中。
  127.           System.arraycopy(elementData, 0, a, 0, size);
  128.           if (a.length > size)
  129.               a[size] = null;
  130.           return a;
  131.       }
  132.       // 獲取index位置的元素值
  133.       public E get(int index) {
  134.           RangeCheck(index);
  135.           return (E) elementData[index];
  136.       }
  137.       // 設置index位置的值為element
  138.       public E set(int index, E element) {
  139.           RangeCheck(index);
  140.           E oldValue = (E) elementData[index];
  141.           elementData[index] = element;
  142.           return oldValue;
  143.       }
  144.       // 將e添加到ArrayList中
  145.       public boolean add(E e) {
  146.           ensureCapacity(size + 1);  // Increments modCount!!
  147.           elementData[size++] = e;
  148.           return true;
  149.       }
  150.       // 將e添加到ArrayList的指定位置
  151.       public void add(int index, E element) {
  152.           if (index > size || index < 0)
  153.               throw new IndexOutOfBoundsException(
  154.               "Index: "+index+", Size: "+size);
  155.           ensureCapacity(size+1);  // Increments modCount!!
  156.           System.arraycopy(elementData, index, elementData, index + 1,
  157.                size - index);
  158.           elementData[index] = element;
  159.           size++;
  160.       }
  161.       // 刪除ArrayList指定位置的元素
  162.       public E remove(int index) {
  163.           RangeCheck(index);
  164.           modCount++;
  165.           E oldValue = (E) elementData[index];
  166.           int numMoved = size - index - 1;
  167.           if (numMoved > 0)
  168.               System.arraycopy(elementData, index+1, elementData, index,
  169.                    numMoved);
  170.           elementData[--size] = null; // Let gc do its work
  171.           return oldValue;
  172.       }
  173.       // 刪除ArrayList的指定元素
  174.       public boolean remove(Object o) {
  175.           if (o == null) {
  176.                   for (int index = 0; index < size; index++)
  177.               if (elementData[index] == null) {
  178.                   fastRemove(index);
  179.                   return true;
  180.               }
  181.           } else {
  182.               for (int index = 0; index < size; index++)
  183.               if (o.equals(elementData[index])) {
  184.                   fastRemove(index);
  185.                   return true;
  186.               }
  187.           }
  188.           return false;
  189.       }
  190.       // 快速刪除第index個元素
  191.       private void fastRemove(int index) {
  192.           modCount++;
  193.           int numMoved = size - index - 1;
  194.           // 從"index+1"開始,用後面的元素替換前面的元素。
  195.           if (numMoved > 0)
  196.               System.arraycopy(elementData, index+1, elementData, index,
  197.                                numMoved);
  198.           // 將最後一個元素設為null
  199.           elementData[--size] = null; // Let gc do its work
  200.       }
  201.       // 刪除元素
  202.       public boolean remove(Object o) {
  203.           if (o == null) {
  204.               for (int index = 0; index < size; index++)
  205.               if (elementData[index] == null) {
  206.                   fastRemove(index);
  207.               return true;
  208.               }
  209.           } else {
  210.               // 便利ArrayList,找到“元素o”,則刪除,並返回true。
  211.               for (<
您的分享是我們最大的動力!

-Advertisement-
Play Games
更多相關文章
  • 在我們的項目經常需要監聽一些鍵盤事件來觸發程式的執行,而Vue中允許在監聽的時候添加關鍵修飾符: 對於一些常用鍵,還提供了按鍵別名: 全部的按鍵別名: .enter .tab .delete (捕獲“刪除”和“退格”鍵) .esc .space .up .down .left .right 修飾鍵: ...
  • 問題:有兩個元素: A, B。兩則是嵌套關係,A是B的父節點。A和B都是塊元素。當在A上設置:margin: 0 auto的時候,B並沒有在頁面中居中。 margin: 0 auto 為什麼沒有生效? 解決:margin:0 auto;生效,需要一定的前提條件。 1 兩者是塊元素,即 display ...
  • 下麵是在變數開始的時候定義初始值 ...
  • Description 聰聰和可可是兄弟倆,他們倆經常為了一些瑣事打起來,例如家中只剩下最後一根冰棍而兩人都想吃、兩個人都想玩兒電腦(可是他們家只有一臺電腦)……遇到這種問題,一般情況下石頭剪刀布就好了,可是他們已經玩兒膩了這種低智商的游戲。他們的爸爸快被他們的爭吵煩死了,所以他發明瞭一個新游戲:由 ...
  • 我們在上一篇搭建了一個簡單的springboot應用,這一篇將介紹使用spring-data-jpa操作資料庫。 新建一個MySQL資料庫,這裡資料庫名為springboot,建立user_info數據表,作為我們示例操作的表對象。 user_info信息如下: 資料庫及表創建成功後,回到我們的工程 ...
  • 好久不發文章了,難道是因為忙,其實是因為懶。這是一篇關於線程池使用和基本原理的科普水文,如果你經常用到線程池,不知道你的用法標準不標準,是否有隱藏的 OOM 風險。不經常用線程池的同學,還有對幾種線程的使用不甚瞭解的同學可以讀一下此文。 為什麼要使用線程池 雖然大家應該都已經很清楚了,但還是說一下。 ...
  • 集合 初次學習集合過程中的學習筆記,學習頂層,使用底層.包括常用的API Collection介面 概述 集合 : 集合是Java中提供的一種容器,可以用來存儲多個數據. 與數組的區別: 數組的長度是固定的,集合的長度是可變的. 數組只能存儲同一種數據類型,集合可以存儲任意數據類型. 數組可以存儲基 ...
  • 原文地址:https://medium.com/karachain/why-i-am-building-a-blockchain-in-go-6395a60b24dd Go語言現在常常被用來做去中心化系統(decentralised system)。其他類型的公司也都把Go用在產品的核心模塊中,並且 ...
一周排行
    -Advertisement-
    Play Games
  • 移動開發(一):使用.NET MAUI開發第一個安卓APP 對於工作多年的C#程式員來說,近來想嘗試開發一款安卓APP,考慮了很久最終選擇使用.NET MAUI這個微軟官方的框架來嘗試體驗開發安卓APP,畢竟是使用Visual Studio開發工具,使用起來也比較的順手,結合微軟官方的教程進行了安卓 ...
  • 前言 QuestPDF 是一個開源 .NET 庫,用於生成 PDF 文檔。使用了C# Fluent API方式可簡化開發、減少錯誤並提高工作效率。利用它可以輕鬆生成 PDF 報告、發票、導出文件等。 項目介紹 QuestPDF 是一個革命性的開源 .NET 庫,它徹底改變了我們生成 PDF 文檔的方 ...
  • 項目地址 項目後端地址: https://github.com/ZyPLJ/ZYTteeHole 項目前端頁面地址: ZyPLJ/TreeHoleVue (github.com) https://github.com/ZyPLJ/TreeHoleVue 目前項目測試訪問地址: http://tree ...
  • 話不多說,直接開乾 一.下載 1.官方鏈接下載: https://www.microsoft.com/zh-cn/sql-server/sql-server-downloads 2.在下載目錄中找到下麵這個小的安裝包 SQL2022-SSEI-Dev.exe,運行開始下載SQL server; 二. ...
  • 前言 隨著物聯網(IoT)技術的迅猛發展,MQTT(消息隊列遙測傳輸)協議憑藉其輕量級和高效性,已成為眾多物聯網應用的首選通信標準。 MQTTnet 作為一個高性能的 .NET 開源庫,為 .NET 平臺上的 MQTT 客戶端與伺服器開發提供了強大的支持。 本文將全面介紹 MQTTnet 的核心功能 ...
  • Serilog支持多種接收器用於日誌存儲,增強器用於添加屬性,LogContext管理動態屬性,支持多種輸出格式包括純文本、JSON及ExpressionTemplate。還提供了自定義格式化選項,適用於不同需求。 ...
  • 目錄簡介獲取 HTML 文檔解析 HTML 文檔測試參考文章 簡介 動態內容網站使用 JavaScript 腳本動態檢索和渲染數據,爬取信息時需要模擬瀏覽器行為,否則獲取到的源碼基本是空的。 本文使用的爬取步驟如下: 使用 Selenium 獲取渲染後的 HTML 文檔 使用 HtmlAgility ...
  • 1.前言 什麼是熱更新 游戲或者軟體更新時,無需重新下載客戶端進行安裝,而是在應用程式啟動的情況下,在內部進行資源或者代碼更新 Unity目前常用熱更新解決方案 HybridCLR,Xlua,ILRuntime等 Unity目前常用資源管理解決方案 AssetBundles,Addressable, ...
  • 本文章主要是在C# ASP.NET Core Web API框架實現向手機發送驗證碼簡訊功能。這裡我選擇是一個互億無線簡訊驗證碼平臺,其實像阿裡雲,騰訊雲上面也可以。 首先我們先去 互億無線 https://www.ihuyi.com/api/sms.html 去註冊一個賬號 註冊完成賬號後,它會送 ...
  • 通過以下方式可以高效,並保證數據同步的可靠性 1.API設計 使用RESTful設計,確保API端點明確,並使用適當的HTTP方法(如POST用於創建,PUT用於更新)。 設計清晰的請求和響應模型,以確保客戶端能夠理解預期格式。 2.數據驗證 在伺服器端進行嚴格的數據驗證,確保接收到的數據符合預期格 ...