一、稀疏數組
當一個數組中大部分元素爲0,或者爲同一個值的數組時,可以使用稀疏數組來保存該數組。
稀疏數組(sparsearray)的處理方式:
- 記錄數組一共有幾行幾列,有多少個不同的值
- 把具有不同值的元素的行列以及值記錄在一個小規模的數組中,從而縮小程序的規模。
二維數組轉稀疏數組的思路
- 遍歷原始的二維數組,得到有效數據(不同的值的數據)的個數sum
- 根據sum可以創建稀疏數組sparseArray int[sum+1][3]
- 將二維數組的行列以及sum寫入數組的第一行。然後將二維數組的有效數據存入到稀疏數組。
代碼實現:
/**
* 將二維數組轉爲稀疏數組
* @param twoDimensional
*/
private static int[][] twoDimensionalToSparseArray(int[][] twoDimensional){
if(twoDimensional.length == 0){
return null;
}
//遍歷得到二維數組一共有多少不同的值
int sum = 0;
for(int[] array : twoDimensional){
for(int value : array){
if(value != 0){
sum++;
}
}
}
//創建稀疏數組
int[][] sparseArray = new int[sum+1][3];
//首先保存第一行數據(二維數組的行、列、多少個不同的值)
sparseArray[0][0] = twoDimensional.length;
sparseArray[0][1] = twoDimensional[0].length;
sparseArray[0][2] = sum;
//遍歷二維數組,將不同的值存入稀疏數組
int count = 0;
for(int i = 0; i < twoDimensional.length;i++){
for(int j = 0; j < twoDimensional[0].length; j++){
if(twoDimensional[i][j] != 0){
//先做加1操作,因爲第一行保存了二維數組的行列信息
count++;
//保存行
sparseArray[count][0] = i;
//保存列
sparseArray[count][1] = j;
//保存值
sparseArray[count][2] = twoDimensional[i][j];
}
}
}
return sparseArray;
}
private static void printArray(int[][] array){
for(int[] arr : array){
for(int a : arr){
System.out.print(a+" ");
}
System.out.println();
}
}
public static void main(String[] args) {
//構造二維數組
//構造一個11*11的二維數組,且第一行第二列爲1,第二行第三列爲2
int[][] twoDimensional = new int[11][11];
twoDimensional[0][1] = 1;
twoDimensional[1][2] = 2;
//打印原始二維數組
System.out.println("原始二維數組");
printArray(twoDimensional);
System.out.println();
//將二維數組轉爲稀疏數組並且打印
int[][] sparseArray = twoDimensionalToSparseArray(twoDimensional);
System.out.println("稀疏數組");
printArray(sparseArray);
}
稀疏數組轉二維數組思路
- 先讀取稀疏數組的第一行,根據第一行的數據(行和列)創建二維數組。
- 在讀取稀疏數組後面幾行的內容,依次賦值給二維數組即可。
代碼實現
/**
* 將稀疏數組轉爲二維數組
* @param sparseArray
* @return
*/
private static int[][] sparseArrayToTwoDimensional(int[][] sparseArray){
if(sparseArray.length == 0){
return null;
}
//讀取稀疏數組的第一行構造二維數組
//行
int row = sparseArray[0][0];
int column = sparseArray[0][1];
int[][] twoDimensional = new int[row][column];
//讀取稀疏數組剩餘部分,循環給二維數組賦值
for(int i = 1; i < sparseArray.length; i++){
twoDimensional[sparseArray[i][0]][sparseArray[i][1]] = sparseArray[i][2];
}
return twoDimensional;
}
public static void main(String[] args) {
//構造二維數組
//構造一個11*11的二維數組,且第一行第二列爲1,第二行第三列爲2
int[][] twoDimensional = new int[11][11];
twoDimensional[0][1] = 1;
twoDimensional[1][2] = 2;
//打印原始二維數組
System.out.println("原始二維數組");
printArray(twoDimensional);
//將二維數組轉爲稀疏數組並且打印
int[][] sparseArray = twoDimensionalToSparseArray(twoDimensional);
System.out.println("稀疏數組");
printArray(sparseArray);
int[][] newTwoDimensional = sparseArrayToTwoDimensional(sparseArray);
System.out.println("還原後的二維數組");
printArray(newTwoDimensional);
}
二 隊列
隊列是一個有序列表,可以使用數組或者鏈表來實現
遵循先入先出原則。即先存入隊列的數據,要先取出,後存入隊列的數據要後取出。
1. 數組模擬隊列的思路
- 隊列本身是有序列表,若使用數組的結構來存儲隊列的數據,因爲隊列的輸出輸入是分別從前後端來處理,因此需要兩個變量front及rear分別表示隊列前後端的下標。front會隨着數據的輸出二改變,rear會隨着數據的輸入而改變。
代碼實現如下:
2. 數組模擬環形隊列
對數組模擬隊列的優化,充分利用數組,因此將數組看做是一個環形的(通過取模的方式來實現)
思路分析:
- front 變量的含義做一個調整:front就指向隊列的第一個元素,也就是說arr[front]就是隊列的第一個元素。
- rear變量的含義做一個調整:rear指向隊列的最後一個元素的後一個位置。因爲希望空出一個空間做爲約定。
- 當隊列滿時,條件時(rear+1)%maxSize=front [滿]
- 當隊列爲空的條件:rear == front 空
- 隊列中的有效數據個數(rear+maxSize-front)%maxSize // rear=1 front=0
尾索引的下一個爲頭索引表示隊列滿
代碼實現
public class MyQueue {
//表示隊列的數組
private int[] queue;
//頭部下標
private int head;
//尾部下標
private int tail;
public MyQueue(int n) {
queue = new int[n];
head = -1;
tail = -1;
}
/**
* 判斷隊列爲空
*
* @return:
* @author: zhaojiaxing
* @createTime: 2019/10/31 0031 22:02
*/
public boolean isEmpty() {
return head == tail ? true : false;
}
/**
* 判斷隊列是否已滿
*
* @return:
* @author: zhaojiaxing
* @createTime: 2019/10/31 0031 22:04
*/
public boolean isFull() {
if (head >= queue.length - 1) {
return true;
}
return false;
}
/**
* 向隊列中放元素
*
* @param num
* @return: int
* @author: zhaojiaxing
* @createTime: 2019/10/31 0031 22:12
*/
public int add(int num) {
if (isFull()) {
throw new RuntimeException("隊列已滿,不能再添加元素");
}
head++;
queue[head] = num;
return queue[head];
}
/**
* 向隊列中取元素
* @param
* @return: int
* @author: zhaojiaxing
* @createTime: 2019/10/31 0031 22:15
*/
public int get() {
if (isEmpty()) {
throw new RuntimeException("隊列爲空,不能再獲取元素");
}
tail++;
return queue[tail];
}
/**
* 打印隊列
* @return:
* @author: zhaojiaxing
* @createTime: 2019/10/31 0031 22:20
*/
public void searchQueue(){
if(isEmpty()){
System.out.println("隊列 爲空");
}
for(int i = tail+1;i<=head;i++){
System.out.print(queue[i]+" ");
}
System.out.println(" ");
}
public static void main(String[] args) {
//初始化隊列
MyQueue queue = new MyQueue(10);
//向隊列中添加元素
try {
for(int i = 0;i < 12;i++){
queue.add((int)((Math.random()+1)*20));
}
} catch (Exception e) {
System.out.println(e.getMessage());
}
queue.searchQueue();
//從隊列中讀取元素
try {
System.out.println("向隊列中獲取元素");
for(int i = 0;i < 12;i++) {
System.out.println(queue.get());
}
} catch (Exception e) {
System.out.println(e.getMessage());
}
queue.searchQueue();
}
}