「藍橋杯」最大子陣詳解

前言:

這題是到簡單的枚舉類型的題目,若你不大明白這題的解法,希望我的方法可以幫助到你。

一.題目:

給定一個 n×m的矩陣 A,求 A 中的一個非空子矩陣,使這個子矩陣中的元素和最大。其中,A的子矩陣指在 A 中行和列均連續的一部分。

輸入格式
輸入的第一行包含兩個整數 n,m(1≤n,m≤50),分別表示矩陣 A 的行數和列數。

接下來 n 行,每行 m 個整數,表示矩陣 Ai,j(−1000≤Ai,j≤1000)。

輸出格式
輸出一行,包含一個整數,表示 A 中最大子矩陣的元素和。

樣例輸入

3 3
2 -4 1
-1 2 1
4 -2 2

樣例輸出

6

二.算法分析

1.首先我們重簡單的查找一位數組的最大子數組開始分析

在這裏插入圖片描述

(1)假設輸入n = 7(n位數組的長度)
(2)定義ans:爲了避免全是負數的情況,我們把ans設置的儘量小一點。
(3)輸入數組
(4)雙重for循環開始從0開始遍歷整個數組
(5)定義sum用來累加子數組中值的和
(6)再來一個for循環是用來防止【j>i】的情況

public class _最大子數組 {
    public static void main(String args[]){
        Scanner sc = new Scanner(System.in);
        int ans = -1005;
        int n = sc.nextInt();
        int arr[] = new int[n];
        for(int i = 0 ; i < n ; i++){
            arr[i] = sc.nextInt();
        }

        for(int i = 0 ; i < n ; i++){
            for(int j = i ; j < n ; j++){
                int sum = 0;
                for(int p = i ; p < j ; p++){
                    sum += arr[p];
                    if(sum > ans){
                        ans = sum;
                  }
                }
            }
        }
        System.out.println(ans);
    }
}

輸入

7
1 2 -3 6 2 -7 1

輸出

8

2.若樓上的一位數組查找最大子數組能明白的話,那麼矩陣查找最大矩陣就可以看成時:二維數組查找最大數組。與一位數組相比,二維數組多了幾行。我們在查找的時候一位數組用雙重for循環,那麼查找二維數組則可用四重for循環。在這裏值得注意的就是ans的設置,爲了避免全是負數的情況,我們把ans設置成-1005,因爲矩陣的極限情況是-1000,所以無論結果多差,ans總是能更新以下。

三.代碼實現

public class _最大子矩陣 {
    public static void main(String args[]){
        Scanner sc = new Scanner(System.in);
        int n = sc.nextInt();
        int m = sc.nextInt();
        int arr[][] = new int[n][m];
        int ans = -1005;
        //輸入數組
        for(int i = 0 ; i < n ; i++){
            for(int j = 0 ; j < m ; j++){
                arr[i][j] = sc.nextInt();
            }
        }
        //查找最小子矩陣
        for(int i = 0 ; i < n ; i++){
            for(int j = i ; j < n ; j++){
                for(int k = 0 ; k < m ; k++){
                    for(int l = k ; l < m ; l++){
                        int sum = 0;
                        for(int p = i ; p <= j ; p++){
                            for(int q = k ; q <= l ; q++){
                                sum += arr[p][q];
                            }
                        }
                        if(sum > ans){
                            ans = sum;
                        }
                    }
                }
            }
        }
        System.out.println(ans);
    }
}

若有不明白的話,希望你可以回覆我,我一定會迅的速回復。若有什麼值得糾正的地方,也希望可以得到回覆。希望大家可以成爲優秀的學習冠軍。

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章