您好,登錄后才能下訂單哦!
這篇文章主要介紹“Array數組的概念和用法”,在日常操作中,相信很多人在Array數組的概念和用法問題上存在疑惑,小編查閱了各式資料,整理出簡單好用的操作方法,希望對大家解答”Array數組的概念和用法”的疑惑有所幫助!接下來,請跟著小編一起來學習吧!
數據結構課程學習筆記。
數組(Array)是一種線性表數據結構。它用一組連續的內存空間,來存儲一組具有相同類型的數據, 并且不支持動態擴容。
線性表就是數據排成一條線一樣的數據結構,每個線性表最多只有前后兩個方向,數組,鏈表丶隊列丶棧等都是線性表數據結構。
非線性表就是數據不規則,與線性表是相對立的,比如二叉樹丶堆丶等,在非線性表中,數據之間并不是簡單的前后關系。
address[i] = base_address + i * data_type_size
address[i] : 下標 i 的地址值。
base_address: 數組的首地址。
data_type_size: 數組中每個元素的大小,也就是數據類型大小(字節),例如int是4個字節。
數組 (Array) 在增刪查這三個動作中,查詢是高效的,但是增和刪是低效的,查詢高效是因為數組支持隨機訪問,時間復雜度是 O(1) ,這里就不多贅述了,但是在增加和刪除的動作中,因為會涉及數據搬移,所以時間復雜度是 O(n) ,下面來詳細講解。
int[] info = new int[6];
數組 info 是一個一維數組,其內容是 33,44,66,77,88 現在需要在下標 2 的位置插入 55 ,將其變成33 44 55 66 77 88的數組,這其中涉及將下標 2 到下標 4 的之間進行數據進行搬移,完成后在下標 2 的位置插入 55 , 其復雜度是 O(n), 但如果是在最后進行插入的話其復雜度是 O(1)。
還拿數組 info 來舉例,數組刪除前其內容是 33,44,00,55,66,77 現在進行刪除操作,刪除下標為 2 內容,這其中涉及將下標 3 到 5 的內容向前搬移,其操作的時間復雜度是 O(n) ,如果是是刪除最后一位且后面沒有內容,則其時間復雜度是O(1) 。
因插入和刪除操作會涉及到數據搬移,所以說他是低效的。
Cpu緩存的最小單位是Cpu緩存行,一個緩存行大小通常是64字節(取決于CPU),試想一下你正在遍歷一個長度為 16 的 long 數組 data[16],原始數據自然存在于主內存中,訪問過程描述如下:
1:訪問 data[0],CPU core 嘗試訪問 CPU Cache,未命中。
2:嘗試訪問主內存,操作系統一次訪問的單位是一個 Cache Line 的大小 — 64 字節,這意味著:既從主內存中獲取3:到了 data[0] 的值,同時將 data[0] ~ data[7] 加入到了 CPU Cache 之中,
4:訪問 data[1]~data[7],CPU core 嘗試訪問 CPU Cache,命中直接返回。
5:訪問 data[8],CPU core 嘗試訪問 CPU Cache,未命中, 嘗試訪問主存,重復步驟2。
因Cpu緩存最小單位是緩存行(64字節),我么來測試一下二維數組的橫向遍歷和縱向遍歷的具體時間和性能。
代碼
package com.com.array; /** * @Auther: lantao * @Date: 2019-06-24 15:52 * @Company: 隨行付支付有限公司 * @maill: lan_tao@suixingpay.com * @Description: TODO */ public class ArrayTest { static long[][] arr; public static void main(String[] args) { long sum = 0L; arr = new long[1024 * 1024][10]; // 橫向遍歷 long l = System.currentTimeMillis(); for (int i = 0; i < 1024 * 1024; i++) { for (int j = 0; j < 10; j++) { sum += arr[i][j]; } } System.out.println("Loop Time 橫向遍歷:" + (System.currentTimeMillis() - l) + "ms"); long l1 = System.currentTimeMillis(); // 縱向遍歷 for (int i = 0; i < 10; i++) { for (int j = 0; j < 1024 * 1024; j++) { sum += arr[j][i]; } } System.out.println("Loop Time 縱向遍歷:" + (System.currentTimeMillis() - l) + "ms"); } }
結果: Loop Time 橫向遍歷:14ms Loop Time 縱向遍歷:83ms
總結: 因橫向遍歷遍歷的是行,然后在循環行的每一列,Cpu緩存會緩存64字節大小的緩存行,所以可以減少cpu和主存之間的交互,直接和高速緩存交互,提升性能,縱向遍歷因每次循環都是不同的行,所以使緩存行沒有作用。
到此,關于“Array數組的概念和用法”的學習就結束了,希望能夠解決大家的疑惑。理論與實踐的搭配能更好的幫助大家學習,快去試試吧!若想繼續學習更多相關知識,請繼續關注億速云網站,小編會繼續努力為大家帶來更多實用的文章!
免責聲明:本站發布的內容(圖片、視頻和文字)以原創、轉載和分享為主,文章觀點不代表本網站立場,如果涉及侵權請聯系站長郵箱:is@yisu.com進行舉報,并提供相關證據,一經查實,將立刻刪除涉嫌侵權內容。