P1541 乌龟棋
题面:https://www.luogu.org/problem/P1541
本题由于每种牌个数<=40
所以设f[a][b][c][d]表示你出了a张爬行牌1,b张爬行牌2,c张爬行牌3,d张爬行牌4时的得分
然后直接枚举每种牌的个数递推即可
Code:
#include<iostream>
#include<cstdio>
#include<cstring>
#include<cstdlib>
#include<cmath>
#include<algorithm>
#include<ctime>
#include<queue>
using namespace std;
const int N=355,M=45;
int n,m,a[N],b,f[M][M][M][M],num[N];
int main(){
scanf("%d%d",&n,&m);
for(int i=1;i<=n;i++){
scanf("%d",&a[i]);
}
for(int i=1;i<=m;i++){
scanf("%d",&b);
num[b]++;
}
f[0][0][0][0]=a[1];
for(int i=0;i<=num[1];i++){
for(int j=0;j<=num[2];j++){
for(int k=0;k<=num[3];k++){
for(int l=0;l<=num[4];l++){
int r=i+j*2+k*3+l*4+1;
if(i!=0){
f[i][j][k][l]=max(f[i][j][k][l],f[i-1][j][k][l]+a[r]);
}
if(j!=0){
f[i][j][k][l]=max(f[i][j][k][l],f[i][j-1][k][l]+a[r]);
}
if(k!=0){
f[i][j][k][l]=max(f[i][j][k][l],f[i][j][k-1][l]+a[r]);
}
if(l!=0){
f[i][j][k][l]=max(f[i][j][k][l],f[i][j][k][l-1]+a[r]);
}
}
}
}
}
printf("%d\n",f[num[1]][num[2]][num[3]][num[4]]);
return 0;
}