YunYan

  博客园  :: 首页  :: 新随笔  :: 联系 :: 订阅 订阅  :: 管理

题目大意:有个人要去参加派对,一共有n场派对,每场派对需要的衣服为a[i],这个人可以同时套上多件衣服,当派对需要的衣服为a[i]时,他可以直接穿上一件a[i],也可以一件件的脱掉,直到身上的衣服为a[i]为止,问这个人最少需要穿几次衣服。

题解:

区间DP问题,定义状态dp[l][r]表示第l场派对到第r场派对共需要穿多少件衣服,该怎么转移呢?可以直接穿上所以dp[l][r]=dp[l][r-1]+1,也可以通过脱掉一定的衣服,dp[l][r]=dp[l][i]+dp[i+1][r-1],要求a[i]=a[r],即我们需要将[i+1,r-1]这几场派对的衣服给脱掉,然后将第i场派对的衣服露出来,dp[l][i]表示从第l天到第i天需要的衣服,dp[i+1][r-1]表示第i+1天到第r-1天需要的衣服,也就是我们需要脱掉的衣服。

code:

#include<bits/stdc++.h>
using namespace std; 
const int N=100+7;
int arr[N];
int dp[N][N];
int time1=0;
void solve(){
    int n;
    cin>>n;
    memset(dp,0,sizeof dp);
    for(int i=1;i<=n;i++) {
        cin>>arr[i];
        dp[i][i]=1;
    }
    for(int i=1;i<n;i++){
        if(arr[i]==arr[i+1]) dp[i][i+1]=1;
        else dp[i][i+1]=2;
    }
    dp[0][0]=0;
    for(int len=2;len<=n;len++){
        for(int l=1,r=len;r<=n;r++,l++){
            dp[l][r]=dp[l][r-1]+1;
            for(int i=l;i<=r-1;i++){
                if(arr[i]==arr[r]) dp[l][r]=min(dp[l][i]+dp[i+1][r-1],dp[l][r]);
            }
        }
    } 
    printf("Case %d: %d\n",++time1,dp[1][n]);
}

int main(){
    int t;cin>>t;
    while(t--) solve(); 
    return 0;
} 

 

posted on 2020-05-19 18:22  Target--fly  阅读(144)  评论(0编辑  收藏  举报