1. 求最大连续子序列
给定K个整数的序列{ N1, N2, ..., NK },其任意连续子序列可表示为{ Ni, Ni+1, ..., Nj },其中 1 <= i <= j <= K。最大连续子序列是所有连续子序列中元素和最大的一个,例如给定序列{ -2, 11, -4, 13, -5, -2 },其最大连续子序列为{ 11, -4, 13 },最大和为20。现在增加一个要求,即还需要输出该子序列的第一个和最后一个元素。
两种方式:
A. 暴力求解法(两层循环进行遍历:时间复杂度:O(n^2))
public static int maxSubSum(int[] a) {
int maxSum = 0;
for (int i = 0; i < a.length; i++) {
int tempSum = 0;
for (int j = i; j < a.length; j++) {
tempSum += a[j];
if (tempSum > maxSum) {
maxSum = tempSum;
}
}
}
return maxSum;
}
B. 动态规划算法:(sum(j) = max(sum(j-1)+aj , aj):时间复杂度:O(n))
public static int maxSubSum(int[] a) {
int maxSum = 0;
int tempSum = 0;
int begin = 0;
int end = 0;
for (int i = 0; i < a.length; i++) {
if (tempSum > 0) {
tempSum += a[i];
} else {
tempSum = a[i];
begin = i; //标记
}
if (tempSum > maxSum) {
maxSum = tempSum;
//可以在这里获取最佳连续子序列和的起点位置begin和重点位置i
end = i;
}
}
return maxSum;
}
2. 斐波那契数列
F(0)=0,F(1)=1, F(n)=F(n-1)+F(n-2)(n>=2,n∈N*)
方法A:递归算法
public int getSum(int n) {
if(n == 0) {
return 0;
}
if(n == 1) {
return 1;
}
return getSum(n-1) + getSum(n-2);
}
public int[] getArray(int[] s) {
int[] t = new int[s.length];
for(int i=0;i<s.length;i++) {
t[i] = getSum(i);
}
return t;
}
方法B:遍历算法:
public int Fibonacci(int n) {
int[] res = {0, 1};
if (n < 2) {
return res[n];
}
int first = 0;
int second = 1;
int fibn = 0;
for (int i = 2; i <= n; i++) {
fibn = first + second;
first = second;
second = fibn;
}
return fibn;
}
public int[] getArray(int[] s) {
int[] t = new int[s.length];
for(int i=0;i<s.length;i++) {
t[i] = Fibonacci(i);
}
return t;
}