一.總述算法
分治算法其實就是將一個大問題分解爲若干個類型相同可是規模較小的子問題,使用遞歸的方式一直分解下去,而後將子問題的解合併獲得原問題的解的策略。c#
二.經典的分治算法列舉spa
二分搜索、大整數乘法、strassen矩陣乘法、棋盤覆蓋、合併排序、快速排序、線性時間選擇、最接近點對問題、循環賽日程表、漢諾塔等code
三.分治算法舉例blog
最大子數列問題:下面是股票的價格變更,求在哪一天買入,哪一天賣出得到的收益最高排序
1.雙重循環實現(不是分治算法)遞歸
1)C#實現及結果string
int[] prices = { 100, 113, 110, 85, 105, 102, 86, 63, 81, 101, 94, 106, 101, 79, 94, 90, 97 }; int profit = prices[1] - prices[0]; int tempProfit = 0; int[] result = { 0, 1 }; for(int i = 0;i < prices.Length;i++) { for(int j = i;j < prices.Length; j++) { tempProfit = prices[j] - prices[i]; if(profit < tempProfit) { profit = tempProfit; result[0] = i; result[1] = j; } } } Console.WriteLine("在第" + result[0] + "天買入,第" + result[1] + "天賣出,所得到利潤最多,每股利潤是" + profit + "元");
2)Lua實現代碼及結果it
prices = { 100, 113, 110, 85, 105, 102, 86, 63, 81, 101, 94, 106, 101, 79, 94, 90, 97 } profit = prices[2] - prices[1] tempProfit = 0 result = { 0, 1 } for i=1,#prices,1 do for j=i,#prices,1 do tempProfit = prices[j] - prices[i]; if (profit < tempProfit) then profit = tempProfit result[0] = i-1 result[1] = j-1 end end end print("在第"..result[0].."天買入,第"..result[1].."天賣出,所得到利潤最多,每股利潤是"..profit.."元")
2.分治算法io
1)c#實現
static void Main(string[] args) { int[] prices = { 100, 113, 110, 85, 105, 102, 86, 63, 81, 101, 94, 106, 101, 79, 94, 90, 97 }; int start = 0; int end = prices.Length - 1; int profit = GetMaxProfit(prices,ref start,ref end); Console.WriteLine("在第" + start + "天買入,第" + end + "天賣出,所得到利潤最多,每股利潤是" + profit + "元"); } static int MaxNumInArray(int[] nums,int start,int end,out int maxNumIndex) { int result = nums[start]; maxNumIndex = start; for(int i = start +1;i <= end; i++) { if (nums[i] > result) { result = nums[i]; maxNumIndex = i; } } return result; } static int MinNumInArray(int[] nums,int start,int end,out int minNumIndex) { int result = nums[start]; minNumIndex = start; for (int i = start + 1; i <= end; i++) { if (nums[i] < result) { result = nums[i]; minNumIndex = i; } } return result; } static int GetMaxProfit(int[] nums,ref int start,ref int end) { if (start == end) return 0; int mid = (start + end) / 2; int crossStart; int crossEnd; int crossProfit = MaxNumInArray(nums,mid + 1,end,out crossEnd) - MinNumInArray(nums,start,mid,out crossStart); int leftStart = start; int leftEnd = mid; int leftProfit = GetMaxProfit(nums,ref leftStart,ref leftEnd); int rightStart = mid + 1; int rightEnd = end; int rightProfit = GetMaxProfit(nums,ref rightStart,ref rightEnd); int result; if(crossProfit > leftProfit && crossProfit > rightProfit) { result = crossProfit; start = crossStart; end = crossEnd; } else if(leftProfit > crossProfit && leftProfit > rightProfit) { result = leftProfit; start = leftStart; end = leftEnd; } else { result = rightProfit; start = rightStart; end = rightEnd; } return result; }
2).Lua實現
prices = { 100, 113, 110, 85, 105, 102, 86, 63, 81, 101, 94, 106, 101, 79, 94, 90, 97 } function MaxNumInArray(nums,smax,emax) resultmax = nums[smax] maxNumIndex = smax for imax = smax,emax,1 do if (nums[imax] > resultmax) then resultmax = nums[imax] maxNumIndex = imax end end return resultmax,maxNumIndex; end function MinNumInArray(nums,smin,emin) resultmin = nums[smin] minNumIndex = smin for i = smin +1,emin,1 do if (nums[i] < resultmin) then resultmin = nums[i] minNumIndex = i end end return resultmin,minNumIndex end function GetMaxProfit(nums,s,e) if s==e then return 1,s,e end local mid = 0; if (s + e) % 2 == 0 then mid = (s + e) / 2 else mid = (s + e - 1) / 2 end local rightMax,crossEnd = MaxNumInArray(nums,mid + 1,e) local leftMin,crossStart = MinNumInArray(nums,s,mid) local crossProfit = rightMax - leftMin local leftProfit,leftStart,leftEnd = GetMaxProfit(nums,s,mid) local rightProfit,rightStart,rightEnd = GetMaxProfit(nums,mid+1,e) if crossProfit > leftProfit and crossProfit > rightProfit then result = crossProfit s = crossStart e = crossEnd elseif (leftProfit > crossProfit and leftProfit > rightProfit) then result = leftProfit s = leftStart e = leftEnd else result = rightProfit; s = rightStart; e = rightEnd; end return result,s,e end profit,s,e = GetMaxProfit(prices,1,#prices) print("在第"..(s-1).."天買入,第"..(e-1).."天賣出,所得到利潤最多,每股利潤是"..profit.."元")