原题链接:蓝桥杯历届试题-最大子阵
解题思路:每一次都将单行或多行的数据加起来形成一行,就可以转换成最大子数组问题,而最大子数组是比较简单的,直接一层循环进行累加,如果之前累加的和小于0,那么就丢弃,从下一个点重新开始计算,否则就可以加上。
注意事项:
参考代码:
//将多行的数据加起来形成一行,就可以转换成最大子数组问题
public static int maxSubMatrix(int[][] matrix) {
if(matrix.length == 0) return 0;
if(matrix[0].length == 0) return 0;
int rows = matrix.length;
int cols = matrix[0].length;
int[] sumOfCol = new int[cols]; //存放每列之和
int max = matrix[0][0];
for(int beginRow = 0; beginRow < rows; beginRow++) //起始行
{
for(int i = beginRow; i < rows; i++)
{
for(int j = 0; j < cols; j++)
{
sumOfCol[j] += matrix[i][j];
}
//转换成求子数组最大和问题
int t = maxSubArray(sumOfCol);
if(t > max)
{
max = t;
}
}
Arrays.fill(sumOfCol, 0); //进行下一轮之前先初始化sumOfCol
}
return max;
}
public static int maxSubArray(int[] arr) {
if(arr.length == 0) return 0;
int sum = arr[0];
int max = arr[0];
for(int i = 1; i < arr.length; i++)
{
//大于等于0就可以带上,否则就丢弃,然后从新开始
if(sum >= 0)
{
sum += arr[i];
}
else
{
sum = arr[i];
}
if(sum > max)
{
max = sum;
}
}
return max;
}
public static void main(String[] args) {
// TODO Auto-generated method stub
Scanner in = new Scanner(System.in);
int n = in.nextInt();
int m = in.nextInt();
int[][] matrix = new int[n][m];
for(int i = 0; i < n; i++)
{
for(int j = 0; j < m; j++)
{
matrix[i][j] = in.nextInt();
}
}
int ans = maxSubMatrix(matrix);
System.out.println(ans);
}0.0分
3 人评分
C语言网提供由在职研发工程师或ACM蓝桥杯竞赛优秀选手录制的视频教程,并配有习题和答疑,点击了解:
一点编程也不会写的:零基础C语言学练课程
解决困扰你多年的C语言疑难杂症特性的C语言进阶课程
从零到写出一个爬虫的Python编程课程
只会语法写不出代码?手把手带你写100个编程真题的编程百练课程
信息学奥赛或C++选手的 必学C++课程
蓝桥杯ACM、信息学奥赛的必学课程:算法竞赛课入门课程
手把手讲解近五年真题的蓝桥杯辅导课程
发表评论 取消回复