线性时间求最大子数组

#include<iostream>
#include<cstdio>
using namespace std;
int main()
{
	int a[100]={13,-3,-25,20,-3,-16,-26,18,20,-7,12,-5,-22,15,-4,7};
	int tsum=0,sum=0,max=-2147483648;
	int f;
	for(int i=0;i<16;++i)
	{
		tsum+=a[i];
		if(tsum<0)
			tsum=0;
		if(tsum>max)
			max=tsum;
	}
	cout<<max<<endl;
	return 0;
}
应该是在算法导论上看到的,这篇笔记距离现在有点久了,记不太清了
在C语言中,求解最大子数组和问题有多种方法,以下为你介绍几种常见的方法: ### 蛮力法 该方法的思路是找出所有子数组,计算所有子数组的和,并从中取最大值。以下是实现代码: ```c #include <stdio.h> // 方法1(蛮力法):两次循环最大子数组之和 int maxSubArray1(int a[], int n) { int i, j; int ThisSum = 0; int MaxSum = 0; for (i = 0; i < n; i++) { ThisSum = 0; for (j = i; j < n; j++) { ThisSum += a[j]; if (ThisSum > MaxSum) { MaxSum = ThisSum; } } } return MaxSum; } int main() { int a[] = {1, -2, 3, 10, -4, 7, 2, -5}; int n = sizeof(a) / sizeof(a[0]); int result = maxSubArray1(a, n); printf("最大子数组和为: %d\n", result); return 0; } ``` ### 优化的暴力法 此方法通过比较一个元素时的最大值,以及相邻2、3、...、n个相邻元素时的最大值来求解。代码如下: ```c #include <stdio.h> #define M 100 int main() { int a[M]; int i, j, N; int m = 0, max = 0; int n; printf("输入数组个数 "); scanf("%d", &n); N = n - 1; printf("输入数组元素 "); for (i = 0; i < n; i++) { scanf("%d", &a[i]); } for (i = 0; i < n; i++) { // 比较一个元素时的最大值 if (a[i] > max) { max = a[i]; } } while (N > 0) { // 比较相邻2,3,...,n个相邻元素时的最大值 for (i = 0; i < N; i++) { m = 0; for (j = 0; j <= (n - N); j++) { // 计算相邻的(n - N + 1)的和,赋给m m = m + a[i + j]; } if (m > max) { max = m; } } N--; } printf("最大为:%d\n", max); return 0; } ``` ### 线性时间复杂度算法 该算法的时间复杂度为O(n),它的核心思想是在遍历数组时,动态更新当前子数组的和以及最大子数组的和。代码如下: ```c #include <stdio.h> // 时间复杂度为O(n)的算法 int maxsum(int a[], int n) { int max = a[0]; // 全负情况,返回最大数 int sum = 0; for (int j = 0; j < n; j++) { if (sum >= 0) { sum = sum + a[j]; // 如果加上某个元素,sum >= 0 的话,就加 } else { sum = a[j]; // 如果加上某个元素,sum < 0 了,就不加 } if (sum > max) { max = sum; } } return max; } int main() { int a[] = {1, -2, 3, 10, -4, 7, 2, -5}; int n = sizeof(a) / sizeof(a[0]); int result = maxsum(a, n); printf("最大子数组和为: %d\n", result); return 0; } ``` ### 另一种线性时间复杂度算法 同样时间复杂度为O(n),该算法在遍历数组时,不断更新当前子数组的和,如果当前和小于0,则将其重置为0。代码如下: ```c #include <stdio.h> // 时间复杂度为O(n)的另一种实现 int MaxSubsequenceSum(const int A[], int N) { int ThisSum, MaxSum, j; ThisSum = MaxSum = 0; for (j = 0; j < N; j++) { ThisSum += A[j]; if (ThisSum > MaxSum) { MaxSum = ThisSum; } else if (ThisSum < 0) { ThisSum = 0; } } return MaxSum; } int main() { int a[] = {1, -2, 3, 10, -4, 7, 2, -5}; int n = sizeof(a) / sizeof(a[0]); int result = MaxSubsequenceSum(a, n); printf("最大子数组和为: %d\n", result); return 0; } ```
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值