java數據結構1--數組、排序和Arrays工具類

數組:Array

  • 數組的定義
  • 數組的內存結構
  • 數組定義常見問題
  • 數組常見操做
  • Java參數傳遞問題--值傳遞
  • 二維數組

1.數組概念

同一種類型數據的集合,能夠是基本數據類型,也能夠是引用數據類型。算法

數組的特色:數組

  1. 數組存儲的都是相同數據類型的元素(相同數據類型
  2. 數組的長度也就是數組中元素的個數(固定長度
  3. 元素從0開始編號,編號也稱「索引」:index(下標,角標)(從零開始
  4. 數組中元素的訪問方式是經過數組名+索引的方式:arr[1](索引訪問

 

數組的定義格式dom

 

2.數組的初始化

初始化方式1:
動態初始化:數組的建立和元素的賦值分開進行
格式:
元素類型[] 數組名 = new 元素類型[數組長度];
int[] arr = new int[3];ide

 


初始化方式2:
靜態初始化:數組建立時就給數組元素賦值
格式:
元素類型[] 數組名 = new 元素類型[]{元素1,元素2,…};
int[] arr = new int[]{2,0,3,1};
靜態初始化的簡化寫法
int[] arr = {2,0,3,1};工具

直接打印數組類型的變量,會發現結果是一段看不懂的字符串,這就是引用數據類型變量的特色,它實際上表明的是一段內存空間的十六進制表示形式.真正的數據在JVM的堆內存空間中。優化

note:動態初始的構成元素都是默認是初始化成默認值的。spa

3.內存結構

Java程序在運行時,爲了提升運行效率,對內存進行了不一樣區域的劃分,每一種區域都有特定的處理數據的方式和內存管理方式
主要有如下幾種:操作系統

  • 棧內存:用於存儲局部變量,當數據使用完,所佔空間會自動釋放
  • 堆內存:存放數組和對象,經過new創建的實例都存放在堆內存中

每個實例都有內存地址值
實例中的變量都有默認初始化值
當實例再也不被使用,會在不肯定的時間被垃圾回收器回收3d

  • 方法區:存放類文件和方法(面向對象部分再講解)
  • 本地方法棧:供本地方法使用,與操做系統相關
  • 程序計數器--Program Counter:對字節碼文件計數

數組的內存結構:不屬於四類八種,因此佔用兩種內存code

4.數組操做常見問題

5.數組的遍歷

數組遍歷:依次訪問每一個元素,訪問的次數就是元素的個數,訪問次數的肯定:length屬性(數組名.length)。

獲取一個數組的最值(最大值,最小值) 改寫:用鍵盤錄入數組的長度和元素值 改寫:數組元素隨機生成,並獲取最值 普通查找:獲取指定元素第一次出現的索引 數組的複製:重點考察是否須要返回值 合併兩個數組 data1 = [1,2,3]  data2 = [4,5,6] 練習:隨機生成兩個數組,併合並 抽取奇數索引的元素(偶數的本身練習) 數組的逆序(注意返回值類型)
練習
public class ArrayDemo4{ public static void main(String[] args){ int[] arr = {8,5,6,9,-10,4}; System.out.println("最大值是: " + getMax(arr)); System.out.println("最小值是: " + getMin(arr)); } //自定義方法,獲取一個數組的最大值
    public static int getMax(int[] arr){ int max = arr[0]; //遍歷餘下的數,比較,大的就放在max中
        for(int i = 1;i<arr.length;i++){ if(arr[i] > max){ max = arr[i]; } } //         return max; } //     public static int getMin(int[] arr){ int min = arr[0]; for(int i = 1;i<arr.length;i++){ if(arr[i] < min){ min = arr[i]; } } return min; } }
獲取一個int數組的最值
public class ArrayDemo5{ public static void main(String[] args){ int[] arr = new int[5]; //循環中產生隨機值,而且賦值給元素
        for(int i = 0;i<arr.length;i++){ int r = (int)(Math.random() * 100 ) + 1; arr[i] = r; } //打印數組元素
 printArray(arr); //獲取最值
        System.out.println("最大值是: " + getMax(arr)); System.out.println("最小值是: " + getMin(arr)); } //     public static int getMax(int[] arr){ int max = arr[0]; for(int i = 1;i<arr.length;i++){ if(arr[i] > max){ max = arr[i]; } } return max; } public static int getMin(int[] arr){ int min = arr[0]; for(int i = 1;i<arr.length;i++){ if(arr[i] < min){ min = arr[i]; } } return min; } //     public static void printArray(int[] arr){ for(int i = 0;i<arr.length;i++){ System.out.print(arr[i] + " "); } System.out.println(); } }
在16-78之間產生5個隨機數組成數組,並求出其中的最值
public class ArrayDemo6{ public static void main(String[] args){ Scanner s = new Scanner(System.in); System.out.print("輸入元素的個數:"); int n = s.nextInt(); //         int[] arr = new int[n]; //賦值
        for(int i = 0;i<arr.length;i++){ System.out.println("輸入第" + (i+1) + "個數:"); arr[i] = s.nextInt(); } //  printArray(arr); } //     public static void printArray(int[] arr){ for(int i = 0;i<arr.length;i++){ System.out.print(arr[i] + " "); } System.out.println(); } }
改寫:用鍵盤錄入數組的長度和元素值
public class ArrayDemo7{ public static void main(String[] args){ int[] arr = {1,2,3,4,5,10,8,2}; Scanner s = new Scanner(System.in); System.out.println("輸入要找的元素:"); int value = s.nextInt(); int index = getIndex(arr,value); //根據返回值判斷是否找到指定元素
        if(index == -1){ System.out.println("沒有找到對應的元素"); }else{ System.out.println("第一次出現的索引是: " + index); } } //int //int[] arr,int value
    public static int getIndex(int[] arr,int value){ /* for(int i = 0;i<arr.length;i++){ if(arr[i] == value){ return i; } } //程序執行到這,意味着沒有發現和參數相等的元素,那就返回一個不存在的索引值 return -1; */
        
        //定義變量,保存返回值
        int index = -1; for(int i = 0;i<arr.length;i++){ if(arr[i] == value){ index = i; break;//不加break,若是屢次出現這個值,那麼這裏獲得的是最後一次出現的索引
 } } return index; } }
普通查找:獲取指定元素第一次出現的索引
public class ArrayDemo8{ public static void main(String[] args){ int[] arr = {3,5,2,0}; int[] res = copyArray(arr); printArray(res); System.out.println(arr == res);//true false
 } //     public static void printArray(int[] arr){ for(int i = 0;i<arr.length;i++){ System.out.print(arr[i] + " "); } System.out.println(); } //自定義方法:實現數組的複製
    public static int[] copyArray(int[] src){ //建立一個新的數組:和源數組同樣長
        int[] dest = new int[src.length]; //循環賦值
        for(int i = 0;i<src.length;i++){ dest[i] = src[i]; } return dest; } }
數組的複製:重點考察是否須要返回值
/* 合併兩個數組 data1 = [1,2,3] data2 = [4,5,6] 分析:先建立一個大的數組:特色長度等於兩個小數組長度之和. 而後依次賦值,重點是目標數組的索引的控制. 練習:隨機生成兩個數組,併合並 隨機生成兩個長度在1-10之內的數組,元組值範圍:1-100 而後合併兩個數組. */

public class ArrayDemo9{ public static void main(String[] args){ int[] data1 = {1,2,3}; int[] data2 = {4,5,6,7,8,9}; int[] dest = merge(data1,data2); printArray(dest); } //自定義方法,實現數組的合併
    public static int[] merge(int[] arr1,int[] arr2){ //建立一個大數組
        int[] dest = new int[arr1.length + arr2.length]; int index = 0; for(int i = 0;i<arr1.length;i++){ dest[index++] = arr1[i]; // index++;
 } for(int i = 0;i<arr2.length;i++){ dest[index++] = arr2[i]; // index++;
 } /* //循環賦值 for(int i = 0;i<arr1.length;i++){ dest[i] = arr1[i]; } for(int i = 0;i<arr2.length;i++){ dest[arr1.length + i] = arr2[i]; } */
        
        return dest; } //     public static void printArray(int[] arr){ for(int i = 0;i<arr.length;i++){ System.out.print(arr[i] + " "); } System.out.println(); } }
合併兩個數組
/* 隨機生成兩個長度在1-10之內的數組,元素值範圍:1-100 而後合併兩個數組. */
public class ArrayDemo10{ public static void main(String[] args){ int l1 = (int)(Math.random() * 10) + 1; int[] arr1 = new int[l1]; int l2 = (int)(Math.random() * 10) + 1; int[] arr2 = new int[l2]; //循環賦值
        for(int i = 0;i<arr1.length;i++){ arr1[i] = (int)(Math.random() * 100) + 1; } //循環賦值
        for(int i = 0;i<arr2.length;i++){ arr2[i] = (int)(Math.random() * 100) + 1; } //打印
        System.out.println("第一個數組是: "); printArray(arr1); System.out.println("-------------"); System.out.println("第二個數組是: "); printArray(arr2); System.out.println("-------------"); System.out.println("合併以後的數組是: "); printArray(merge(arr1,arr2)); } //打印數組
    public static void printArray(int[] arr){ System.out.print("["); for(int i = 0;i<arr.length;i++){ if(i == arr.length - 1){ System.out.print(arr[i] + "]"); }else{ System.out.print(arr[i] + ", "); } } System.out.println(); } //合併數組
    public static int[] merge(int[] src1,int[] src2){ int[] dest = new int[src1.length + src2.length]; int index = 0; for(int i = 0;i<src1.length;i++){ dest[index++] = src1[i]; } for(int i = 0;i<src2.length;i++){ dest[index++] = src2[i]; } return dest; } }
合併兩個數組
public class ArrayDemo11{ public static void main(String[] args){ int[] arr = {1,2,3,4,5,6,7,8,9,10}; int[] odd = getOdd(arr); printArray(odd); int[] even = getEven(arr); printArray(even); } //自定義方法,抽取偶數索引的元素
    public static int[] getEven(int[] arr){ //計算偶數元素的個數
        int n = (arr.length + 1) / 2; //建立新數組
        int[] dest = new int[n]; int index = 0; //循環賦值
        for(int i = 0;i<arr.length;i += 2){ dest[index++] = arr[i]; } return dest; } //自定義方法,抽取奇數索引的元素
    public static int[] getOdd(int[] arr){ //計算奇數索引的個數
        int n = arr.length / 2; //建立目標數組
        int[] dest = new int[n]; int index = 0; //賦值
        for(int i = 0;i<arr.length;i++){ if(i % 2 == 1){ dest[index++] = arr[i]; } } return dest; } //打印數組
    public static void printArray(int[] arr){ System.out.print("["); for(int i = 0;i<arr.length;i++){ if(i == arr.length - 1){ System.out.print(arr[i] + "]"); }else{ System.out.print(arr[i] + ", "); } } System.out.println(); } }
抽取奇數索引的元素
public class ArrayDemo12{ public static void main(String[] args){ int[] arr = {1,2}; reverse(arr); printArray(arr); } //打印數組
    public static void printArray(int[] arr){ System.out.print("["); for(int i = 0;i<arr.length;i++){ if(i == arr.length - 1){ System.out.print(arr[i] + "]"); }else{ System.out.print(arr[i] + ", "); } } System.out.println(); } //     public static void reverse(int[] arr){ int n = arr.length / 2; for(int i = 0;i<n;i++){ int temp = arr[i]; arr[i] = arr[arr.length - 1 - i]; arr[arr.length -1 - i] = temp; } } }
數組的逆序(注意返回值類型)void

6.Java中參數傳遞(實參->形參)的問題

 

public class Test5 { public static void main(String[] args) { int[] a = { 1, 2, 3, 4, 5 }; int[] b = new int[a.length]; System.out.println("交換前:"); print(a); print(b); b = swap(a);//交換
 System.out.println("交換後:"); print(a); print(b); } public static void print(int[] arr){ System.out.print("["); for(int i = 0;i<arr.length;i++){ if(i == arr.length - 1){ System.out.print(arr[i] + "]"); }else{ System.out.print(arr[i] + ", "); } } System.out.println(); } private static int[] swap(int[] c) { int[] tmp = new int[c.length]; for (int j = 0; j < c.length; j++) { tmp[j] = c[c.length - j - 1] + 10; } return tmp; } }
值傳遞1

交換前:
[1, 2, 3, 4, 5]
[0, 0, 0, 0, 0]
交換後:
[1, 2, 3, 4, 5]
[15, 14, 13, 12, 11]

swap()方法時,數組a將其地址傳遞c,因此a和c是指向同一個數組。
但在swap方法中,新生成了一個數組tmp,改變的是tmp數組,返回時把tmp數組的首地址送數組b.因此b指向改tmp.

public class Test6 { public static void main(String[] args) { int[] a = { 1, 2, 3, 4, 5 }; int[] b = new int[a.length]; System.out.println("交換前:"); print(a); print(b); b = swap(a); System.out.println("交換後:"); print(a); print(b); } public static void print(int[] arr){ System.out.print("["); for(int i = 0;i<arr.length;i++){ if(i == arr.length - 1){ System.out.print(arr[i] + "]"); }else{ System.out.print(arr[i] + ", "); } } System.out.println(); } private static int[] swap(int[] c) { for (int j = 0; j < c.length; j++) { c[j] = c[c.length - j - 1] + 10; } return c; } }
值傳遞2
交換前: [1, 2, 3, 4, 5] [0, 0, 0, 0, 0] 交換後: [15, 14, 13, 24, 25] [15, 14, 13, 24, 25]

說明: 在該程序中,在調用swap()方法時,數組a將其地址傳遞給數組c,因此a和c是指向同一個數組。
返回時,數組b再也不指向原來的數組,而指向c所在的數組。
注: JAVA中參數傳遞時是值傳遞,引用型與基本數據類型是不一樣的.

 7 二維數組

7.1二維數組的概念 

7.2 二維數組的定義

注意事項:

1.使用格式1,2時必須指定第一維長度
2.動態,靜態初始化不能同時使用

 

7.3二維數組的遍歷

8 數組的排序(排序算法)

8.1冒泡排序:bubble

冒泡排序(BubbleSort)的基本概念是:依次比較相鄰的兩個數,將小數放在前面,大數放在後面。即首先比較第1個和第2個數,將小數放前,大數放後。而後比較第2個數和第3個數,將小數放前,大數放後,如此繼續,直至比較最後兩個數,將小數放前,大數放後。重複以上過程,仍從第一對數開始比較(由於可能因爲第2個數和第3個數的交換,使得第1個數再也不小於第2個數),將小數放前,大數放後,一直比較到最大數前的一對相鄰數,將小數放前,大數放後,第二趟結束,在倒數第二個數中獲得一個新的最大數。如此下去,直至最終完成排序。

/* * 冒泡排序: * 相鄰的元素兩兩比較.大的日後放. */
public class BubbleSortDemo { public static void main(String[] args) { int[] arr = {9,5,2,0,4,5,5,7}; bubbleSort(arr); printArray(arr); } public static void printArray(int[] arr){ for (int i = 0; i < arr.length; i++) { System.out.print(arr[i] + " "); } System.out.println(); } //     public static void bubbleSort(int[] arr){ //外層循環控制的是比較的趟數:固定是元素個數-1
        for(int i = 0;i<arr.length - 1;i++){ //內層循環控制的是兩兩比較元素的索引
            for(int j = 0;j<arr.length - 1 - i;j++){ if(arr[j] > arr[j + 1]){ int temp = arr[j]; arr[j] = arr[j + 1]; arr[j + 1] = temp; } } } } }
冒泡排序

 

8.2 比較排序:compare(選擇排序:select)

/* * 選擇排序 */
public class SelectSortDemo { public static void main(String[] args) { // TODO Auto-generated method stub
        int[] arr = {9,5,2,7,0,6,4,7}; selectSort(arr); print(arr); } public static void print(int[] arr){ for (int i = 0; i < arr.length; i++) { System.out.print(arr[i] + " "); } System.out.println(); } public static void selectSort(int[] arr){ //外層控制的是比較的趟數
        for (int i = 0; i < arr.length -1; i++) { //內層循環控制的是兩兩比較元素的索引值
            for (int j = i + 1; j < arr.length; j++) { //                 if(arr[i] > arr[j]){ int temp = arr[i]; arr[i] = arr[j]; arr[j] = temp; } } } } }
選擇排序
public class SelectSortDemo2 { public static void main(String[] args) { //產生1000個元素的數據進行比較
        int[] arr1 = getArray(); int[] arr2 = arrayCopy(arr1); print(arr1); print(arr2); long start = System.currentTimeMillis(); selectSort(arr1); System.out.println(System.currentTimeMillis() - start); start = System.currentTimeMillis(); selectSort2(arr2); System.out.println(System.currentTimeMillis() - start); System.out.println("排序後"); print(arr1); print(arr2); } public static int[] arrayCopy(int[] arr){ int[] dest = new int[arr.length]; System.arraycopy(arr, 0, dest, 0, arr.length); return dest; } //隨機生成1000個元素的int數組
    public static int[] getArray(){ int[] arr = new int[1000]; for(int i = 0;i<arr.length;i++){ arr[i] = (int)(Math.random() * 1000); } return arr; } public static void print(int[] arr){ for (int i = 0; i < arr.length; i++) { System.out.print(arr[i] + " "); } System.out.println(); } public static void selectSort(int[] arr){ int count = 0; //外層控制的是比較的趟數
        for (int i = 0; i < arr.length -1; i++) { //內層循環控制的是兩兩比較元素的索引值
            for (int j = i + 1; j < arr.length; j++) { //                 if(arr[i] > arr[j]){ int temp = arr[i]; arr[i] = arr[j]; arr[j] = temp; count++; } } } System.out.println("優化前的方法中,交換的次數是: " + count); } public static void selectSort2(int[] arr){ int count = 0; //外層控制的是比較的趟數
        for (int i = 0; i < arr.length -1; i++) { //記錄要肯定的元素的索引號
            int index = i; //內層循環控制的是兩兩比較元素的索引值
            for (int j = i + 1; j < arr.length; j++) { //                 if(arr[index] > arr[j]){ index = j; } } //對index值進行判斷
            if(i != index){ int temp = arr[i]; arr[i] = arr[index]; arr[index] = temp; count++; } } System.out.println("優化後的方法中,交換的次數是: " + count); } }
選擇排序比較

9 Arrays工具類

一下皆爲靜態方法。

  1. binarySearch:複製指定的數組
  2. copyOf:複製指定的數組
  3. copyOfRange:將指定數組的指定範圍複製到一個新數組
  4. deepEquals:若是兩個指定數組彼此是深層相等
  5. deepToString:返回指定數組「深層內容」的字符串表示形式。
  6. deepHashCode:基於指定數組的「深層內容」返回哈希碼。
  7. equals:若是兩個指定的 某 型數組彼此相等,則返回 true。
  8. fill: 將指定的 某型 值分配給指定 某 型數組的每一個元素。
  9. sort:根據元素的天然順序對指定某類型數組按升序進行排序。
  10. toString:返回指定數組內容的字符串表示形式。

單獨介紹一下二分查找:

public class BinarySearchDemo { public static void main(String[] args) { int[] arr = {1,2,3,7,9,20}; int index = getIndex(arr,1); if(index == -1){ System.out.println("not found"); }else{ System.out.println("the index is : " + index); } } //二分查找算法
    public static int getIndex(int[] arr,int value){ int min = 0; int max = arr.length - 1; int mid = (min + max)/2; while(true){ //             if(arr[mid] == value){ return mid; }else if(arr[mid] > value){ max = mid - 1; }else{ min = mid + 1; } //從新計算mid的值
            mid = (min + max)/2; //             if(min > max){ return -1; } } } }
二分查找:前提:數組必須有序:
相關文章
相關標籤/搜索