这道题思路比较简单,看懂这句话你也就会了:如果最后一家店还能洗劫,而且不惊动警察,那么一定要去洗劫
分析得递归搜索图:
1.暴力dfs
#include <iostream>
#include <algorithm>
#include <cstring>
using namespace std;
const int N = 1010;
int n,t;
int g[N];
int dfs(int x)
{
if(x>n)
return 0;
else
return max(dfs(x+1),dfs(x+2)+g[x]);
}
int main(void)
{
cin>>t;
while(t--)
{
scanf("%d",&n);
for(int i=1;i<=n;i++)
{
scanf("%d",&g[i]);
}
int res=dfs(1);
printf("%d\n",res);
}
return 0;
}
2.暴力dfs+记忆化搜索
#include <iostream>
#include <algorithm>
#include <cstring>
using namespace std;
const int N = 1010;
int n,t;
int g[N];
int mem[N];
int dfs(int x)
{
int sum=0;
if(mem[x])
return mem[x];
if(x>n)
sum=0;
else
sum=max(dfs(x+1),dfs(x+2)+g[x]);
mem[x]=sum;
return sum;
}
int main(void)
{
cin>>t;
while(t--)
{
scanf("%d",&n);
memset(mem,0,sizeof(mem));
for(int i=1;i<=n;i++)
{
scanf("%d",&g[i]);
}
int res=dfs(1);
printf("%d\n",res);
}
return 0;
}
3.逆序dp(自下而上)
#include <iostream>
#include <algorithm>
#include <cstring>
using namespace std;
const int N = 1010;
int n,t;
int f[N],g[N];
int main(void)
{
cin>>t;
while(t--)
{
scanf("%d",&n);
for(int i=1;i<=n;i++)
{
scanf("%d",&g[i]);
}
memset(f,0,sizeof(f));
for(int i=n;i>=1;i--)
{
f[i]=max(f[i+1],f[i+2]+g[i]);
}
printf("%d\n",f[1]);
}
return 0;
}
4.dp顺序(自上而下)
#include <iostream>
#include <algorithm>
#include <cstring>
using namespace std;
const int N = 1010;
int n,t;
int f[N],g[N];
int main(void)
{
cin>>t;
while(t--)
{
scanf("%d",&n);
for(int i=1;i<=n;i++)
{
scanf("%d",&g[i]);
}
memset(f,0,sizeof(f));
for(int i=1;i<=n;i++)
{
f[i]=max(f[i-1],f[i-2]+g[i]);
}
printf("%d\n",f[n]);
}
return 0;
}