/*************************************************************************
> File Name: MaxSumOfSubarray.cpp
> Author: Shaojie Kang
> Mail: kangshaojie@ict.ac.cn
> Created Time: 2015年09月11日 星期五 09时13分02秒
> Problem:
求出数组中子数组的最大和、最小和
************************************************************************/
#include<iostream>
#include<vector>
using namespace std;
// Solution 1: one dimention
int GetMaxSum(vector<int> &nums)
{
int size = nums.size();
if(size == 0) return 0;
if(size == 1) return nums[0];
int sum = nums[0];
int curSum = nums[0];
for(int i = 1; i < size; ++i)
{
if(curSum < 0) curSum = 0;
curSum += nums[i];
if(curSum > sum) sum = curSum;
}
return sum;
}
int GetMinSum(vector<int> &nums)
{
int size = nums.size();
if(size == 0) return 0;
if(size == 1) return nums[0];
int sum = nums[0];
int curSum = nums[0];
for(int i = 1; i < size; ++i)
{
if(curSum > 0) curSum = 0;
curSum += nums[i];
if(curSum < sum) sum = curSum;
}
return sum;
}
// Solution 2: two dimentions
void GenerateArea(const vector<vector<int> > &nums, vector<vector<int> > &area)
{
int rows = nums.size();
int cols = nums[0].size();
for(int j = 0; j < cols; ++j)
{
if(j == 0) area[0][j] = nums[0][j];
area[0][j] = area[0][j-1] + nums[0][j];
}
for(int i = 0; i < rows; ++i)
{
if(i == 0) area[i][0] = nums[i][0];
area[i][0] = area[i-1][0] + nums[i][0];
}
for(int i = 1; i < rows; ++i)
{
for(int j = 1; j < cols; ++j)
{
area[i][j] = area[i-1][j] + area[i][j-1] - area[i-1][j-1] + nums[i][j];
}
}
}
int GetBlockSum(const vector<vector<int> > &area, int rowUp, int rowDown, int col)
{
int sum = area[rowDown][col] - area[rowUp][col] - area[rowDown][col-1] + area[rowUp][col-1];
}
int GetMaxSumII(vector<vector<int> > &nums)
{
if(nums.empty()) return 0;
int rows = nums.size();
int cols = nums[0].size();
vector<vector<int> > area(rows, vector<int>(cols, 0));
GenerateArea(nums, area);
int maxSum = nums[0][0];
for(int rowUp = 0; rowUp < rows; ++rowUp)
{
for(int rowDown = rowUp; rowDown < rows; ++rowDown)
{
int sum = GetBlockSum(area, rowUp, rowDown, 0);
int curSum = sum;
for(int col = 1; col < cols; ++cols)
{
if(curSum < 0) curSum = 0;
curSum += GetBlockSum(area, rowUp, rowDown, col);
if(curSum > sum) sum = curSum;
}
if(sum > maxSum) maxSum = sum;
}
}
return maxSum;
}
int main()
{
int arr[] = {
1, -2, 3, 5, -3, 2
};
vector<int> nums(arr, arr + sizeof(arr)/sizeof(int));
cout<<GetMaxSum(nums)<<endl;
cout<<GetMinSum(nums)<<endl;
return 0;
}
/*************************************************************************
> File Name: LongestIncreasingSubSequence.cpp
$ Author: Shaojie Kang
> Mail: kangshaojie@ict.ac.cn
> Created Time: 2015年09月11日 星期五 10时01分59秒
> Problem:
求最长递增子序列
************************************************************************/
#include<iostream>
#include<vector>
using namespace std;
vector<int> GenerateLIS(const vector<int> &nums)
{
vector<int> result;
int size = nums.size();
if(size == 0) return result;
if(size == 1) return nums;
vector<vector<int> > sequences(size);
int longestIndex = 0;
for(int i = 0; i < size; ++i)
{
sequences[i].push_back(nums[i]);
for(int j = 0; j < i; ++j)
{
if(nums[i] > nums[j] && sequences[i].size()+1 > sequences[j].size())
{
sequences[i].clear();
sequences[i].insert(sequences[i].begin(), sequences[j].begin(), sequences[j].end());
sequences[i].push_back(nums[i]);
}
}
if(sequences[i].size() > sequences[longestIndex].size())
longestIndex = i;
}
return sequences[longestIndex];
}
int main()
{
int arr[] = {
3, 2, 9, 1, 4, 2, 6, 3, 7, 8, 9
};
vector<int> nums(arr, arr + sizeof(arr)/sizeof(int));
vector<int> result = GenerateLIS(nums);
for(int i = 0; i < result.size(); ++i)
cout<<result[i]<<" ";
cout<<endl;
return 0;
}