方法1:暴力計算法
i 表示子列開始索引
j 表示子列結束索引
k(i
public三層for迴圈,時間複雜度 t(n) = n^3int method1(int
arr)
if (tempmax >maxsum) }}
return
maxsum;
}
方法2:暴力破解優化
因為方法一每次都是從 i 加到 j ,而 j 每次只往後掃瞄變化乙個,所以直接將 k 迴圈省略在 j 迴圈中計算
public兩層for迴圈,t(n) = n^2int method2(int
arr)
} }
return
maxsum;
}
方法3:分治策略,將問題劃分為更小的問題,解決後再返回來求最優解
/**t(n) = t(n/2) + cn* 為了與方法1和2有同樣的呼叫介面
* @param
arr *
@return
*/public
int method3(int
arr)
/*** 將陣列劃分為兩部分,先計算左半部分最大子列和,再計算又半部分最大子列和,再從分界線向左向右分別掃瞄獲取最大子列和取得跨界最大子列和**
@param
arr *
@param
left
* @param
right
* @return
*/private
int divideandconquer(int arr, int left, int
right)
else
}/*下面是"分"的過程
*/int mid = (left + right) / 2;
/*求最大左子列和
*/int maxleftsum =divideandconquer(arr, left, mid);
/*求最大右子列和
*/int maxrightsum = divideandconquer(arr, mid + 1, right);
/*求跨界最大子列和
*/int maxleftbordersum = 0;
int maxrightbordersum = 0;
int leftbordersum = 0;
int rightbordersum = 0;
/*從中線向左掃瞄
*/for (int i = mid; i >= left; i--)
}/*從中線向右掃瞄
*/for (int i = mid + 1; i < right; i++)
}/*返回該分段中最左,最右,跨界三者中最大數作為該分段最大子列和
*/return max3(maxleftsum, maxrightsum, maxleftbordersum +maxrightbordersum);
}/*** 求三整數最大值
* 計算順序
* a > b ? (a > c ? a : c) : (b > c ? b : c)
* @param
a *
@param
b *
@param
c *
@return
*/private
int max3(int a, int b, int
c)
求解得時間複雜度 t(n) = nlogn
/****每個元素最少都要掃瞄一遍,時間複雜度t(n) = n@param
arr
*/public
int method4(int
arr) else
if (tempmax < 0)
}return
maxseqsum;
}
執行**
public執行結果class
searchmaxqueuesum ;
searchmaxqueuesum searchmaxqueuesum = new
searchmaxqueuesum();
int seqsumfrommethod1 =searchmaxqueuesum.method1(arr);
int seqsumfrommethod2 =searchmaxqueuesum.method3(arr);
int seqsumfrommethod3 =searchmaxqueuesum.method3(arr);
int seqsumfrommethod4 =searchmaxqueuesum.method4(arr);
system.out.println("method1: "+seqsumfrommethod1);
system.out.println("method2: "+seqsumfrommethod2);
system.out.println("method3: "+seqsumfrommethod3);
system.out.println("method4: "+seqsumfrommethod4);
}public
int method1(int
arr)
if (tempmax >maxsum) }}
return
maxsum;
}public
int method2(int
arr) }}
return
maxsum;
}/*** 為了與方法1和2有同樣的呼叫介面
* @param
arr *
@return
*/public
int method3(int
arr)
/*** 將陣列劃分為兩部分,先計算左半部分最大子列和,再計算又半部分最大子列和,再從分界線向左向右分別掃瞄獲取最大子列和取得跨界最大子列和**
@param
arr *
@param
left
* @param
right
* @return
*/private
int divideandconquer(int arr, int left, int
right)
else
}/*下面是"分"的過程
*/int mid = (left + right) / 2;
/*求最大左子列和
*/int maxleftsum =divideandconquer(arr, left, mid);
/*求最大右子列和
*/int maxrightsum = divideandconquer(arr, mid + 1, right);
/*求跨界最大子列和
*/int maxleftbordersum = 0;
int maxrightbordersum = 0;
int leftbordersum = 0;
int rightbordersum = 0;
/*從中線向左掃瞄
*/for (int i = mid; i >= left; i--)
}/*從中線向右掃瞄
*/for (int i = mid + 1; i < right; i++)
}/*返回該分段中最左,最右,跨界三者中最大數作為該分段最大子列和
*/return max3(maxleftsum, maxrightsum, maxleftbordersum +maxrightbordersum);
}/*** 求三整數最大值
* 計算順序
* a > b ? (a > c ? a : c) : (b > c ? b : c)
* @param
a *
@param
b *
@param
c *
@return
*/private
int max3(int a, int b, int
c)
/** *
* @param
arr
*/public
int method4(int
arr) else
if (tempmax < 0)
}return
maxseqsum;}}
求最大子列和問題
給定k個整數組成的序列,連續子列 被定義為,其中 1 i j k。最大子列和 則被定義為所有連續子列元素的和中最大者。例如給定序列,其連續子列有最大的和20。在此方法中用了三個迴圈,第一層是子列左端,第二層是子列右端,裡層為子列的求和。t n o n 3 int thissum maxsum 0 i...
求最大子列和
給定乙個含有n整數的序列,求其最大子列和 即該序列中一段連續子串行和的最大值 大致思路是 定義乙個當前位置之前的序列和的最大值 maxsum 以及當前子串行的和 thissum 每迭代一次比較二者的大小關係,如果maxsum小於thissum,則更新maxsum,否則繼續遍歷。當thissum 0時...
分而治之 求最大子列和
小白乙隻,這個程式想實現輸入乙個陣列,求出最大子列和,能執行但是不對。可否給予我一些指點。include intmax3 int a,int b,int c intdivideandconquer char list,int left,int right 下面是 分 的過程 center left ...