动态规划一一线性动态规划

先说一下对动态规划的理解:这是一种针对段阶段问题的最优化问题的一种解法。具有最优子结构性质,局部最优与整体最优。具有子问题重叠特征,动态规划通过对子问题运行与否的记录,减少了运行次数。

动态规划实质是:记忆化搜索。

基本解题步骤:、1.分析问题的最优解,找出最优解的性质,并刻画其结构特征;

        
2、递归地定义最优值;

        
3、采用自底向上的方式计算问题的最优值;

        
4、根据计算最优值时得到的信息,构造最优解。

一。最长公共子序列问题。

最长公共子序列:字符序列的子序列是指从给定字符序列中随意地(不一定连续)去掉若干个字符(可能一个也不去掉)后所形成的字符序列。求任意两个数列的最长公共走序列。

基本思路:引进二维数组记录x[i]与y[i]的lcs长度。

递归关系:c[i][j]=0,  i=0,j=0;

     c[i][j]=c[i-][j-1]+1; i,j>0,x[i]=y[i];

     c[i][j]=max(c[i][j-1],c[i-1][j]) i,j>0,x[i]!=y[i];

代码:

#include<iostream>
#include<cstring>
using namespace std;
int longest (char a[],char b[],int m,int n);
int main()
{
int n,m,p,q;char a[10000],b[10000];
cin>>n;
while(n--)
{

cin>>a>>b;
p=strlen(a);q=strlen(b);
m=longest(a,b,q,p);
cout<<m<<endl;
}
return 0;
}
int longest (char a[],char b[],int m,int n)
{int s[100][100],i,j;
for(i=0;i<=n;i++)
s[i][0]=0;
for(j=1;j<=m;j++)
s[0][j]=0;
for(i=1;i<=n;i++)
for(j=1;j<=m;j++)
{if(a[i-1]==b[j-1])
s[i][j]=s[i-1][j-1]+1;
else
{if(s[i-1][j]>=s[i][j-1])
s[i][j]=s[i-1][j];
else
s[i][j]=s[i][j-1];
}
}
return s[n][m];

}

二。

    最大字段和

给定n个整数(可能有负数)组成的数列,钻出相邻子段使其和最大,输出最大和,并确定子段数列。

#define num 1001

int a[num];

int max(int n,unt&besti,int&bestj)

{

    int sum=0,b=0,begin=0;

for(int i=1;i<=n;i++)

{if(b>0) b+=a[i];

 else {b=a[i];begin=i}

if(b>sum) {sum=b;besti=begin;bestj=i;}

}

return sum;

}

三。

数字三角形

从顶点出发在节点处选择向左或向右,一直到最底层,使其经过的数字和最大。

例题。cows bowling:

Problem Description
The cows don't use actual bowling balls when they go bowling. They each take a number (in the range 0..99), though, and line up in a standard bowling-pin-like triangle like this: 

          7


3 8

8 1 0

2 7 4 4

4 5 2 6 5
Then the other cows traverse the triangle starting from its tip and moving "down" to one of the two diagonally adjacent cows until the "bottom" row is reached. The cow's score is the sum of the numbers of the cows visited along the way. The cow with the highest score wins that frame. 

Given a triangle with N (1 <= N <= 350) rows, determine the highest possible sum achievable.
 

 

Input
Line 1: A single integer, N 

Lines 2..N+1: Line i+1 contains i space-separated integers that represent row i of the triangle.
 

 

Output
Line 1: The largest sum achievable using the traversal rules
 

 

Sample Input
5 7 3 8 8 1 0 2 7 4 4 4 5 2 6 5
 

 

Sample Output
30
 
代码:

#include<iostream>
using namespace std;
int tri[100][100];
int triangle(int n)
{
int i,j;
for(i=n-2;i>=0;i--)
for(j=0;j<=i;j++)
{
if(tri[i+1][j]>tri[i+1][j+1])
tri[i][j]+=tri[i+1][j];
else tri[i][j]+=tri[i+1][j+1];
}
return tri[0][0];
}
int main()
{
int n,i,j;
cin>>n;
for(i=0;i<n;i++)
for(j=0;j<i+1;j++)
cin>>tri[i][j];
cout<<triangle(n)<<endl;
return 0;
}

四。

最长不下降序列。

Problem Description
A numeric sequence of ai is ordered if a1 < a2 < ... < aN. Let the subsequence of the given numeric sequence (a1a2, ..., aN) be any sequence (ai1ai2, ..., aiK), where 1 <= i1 < i2 < ... < iK <= N. For example, sequence (1, 7, 3, 5, 9, 4, 8) has ordered subsequences, e. g., (1, 7), (3, 4, 8) and many others. All longest ordered subsequences are of length 4, e. g., (1, 3, 5, 8).

Your program, when given the numeric sequence, must find the length of its longest ordered subsequence.
 

 

Input
The first line of input file contains the length of sequence N. The second line contains the elements of sequence - N integers in the range from 0 to 10000 each, separated by spaces. 1 <= N <= 1000
 

 

Output
Output file must contain a single integer - the length of the longest ordered subsequence of the given sequence.
 

 

Sample Input
7 1 7 3 5 9 4 8
 

 

Sample Output
4
 

 代码:

#include<iostream>
#include<cstring>
using namespace std;
int a[1002];
int longest(int n)
{
int b[1002],i,j;
for(i=1;i<=n;i++)
b[i]=1;
int max=0;
for(i=2;i<=n;i++)
{int k=0;
for(j=1;j<i;j++)
if(a[i]>a[j]&&k<b[j])
{k=b[j];
b[i]=k+1;}
if(max<b[i])
max=b[i];
}
return max;
}
int main()
{
int n,i;
cin>>n;
for(i=1;i<=n;i++)
cin>>a[i];
for(i=1;i<=n;i++)
if(a[i]<0||a[i]>10000) return 0;
if(n==1) cout<<1<<endl;
else
cout<<longest(n)<<endl;
return 0;
}

posted on 2013-08-08 21:44  留梦言  阅读(465)  评论(0编辑  收藏  举报

导航