hdu 4352 XHXJ's LIS --- 数位dp 状态压缩

来源:互联网 发布:如何进行seo 编辑:程序博客网 时间:2024/05/20 21:47

dp[i][j][k]表示当前位是第i位 选取状态为j 要求长度为k 的个数


#include <iostream>#include <cstring>#include <string>#include <cstdio>#include <cmath>#include <algorithm>#include <vector>#include <queue>#include <map>#define inf 0x3f3f3f3f#define ll __int64using namespace std;ll l,r,k,dp[21][1<<10][11];int num[21];ll dfs(ll n,ll pos,ll len,bool flag){    if(pos==-1) return len==k;    if(!flag&&dp[pos][n][k]!=-1) return dp[pos][n][k];    int p=flag?num[pos]:9;    ll ans=0;    int i,j;    for(i=0;i<=p;i++)    {        if(n||i)        {            if((1<<i)>n)                ans+=dfs(n|(1<<i),pos-1,len+1,flag&&i==p);            else if((1<<i)&n)                ans+=dfs(n,pos-1,len,flag&&i==p);            else            {                for(j=i+1;j<=9;j++)                {                    if((1<<j)&n)                    {                        ans+=dfs(((1<<i)|n)^(1<<j),pos-1,len,flag&&i==p);                        break;                    }                }            }        }        else ans+=dfs(n,pos-1,len,flag&&i==p);    }    if(!flag&&dp[pos][n][k]==-1) dp[pos][n][k]=ans;    return ans;}ll cal(ll x){    int l=0;    while(x)    {        num[l++]=x%10;        x/=10;    }    return dfs(0,l-1,0,1);}int main(){    int t=0,T;    scanf("%d",&T);    memset(dp,-1,sizeof dp);    while(T--)    {        t++;        scanf("%I64d%I64d%I64d",&l,&r,&k);        printf("Case #%d: %I64d\n",t,cal(r)-cal(l-1));    }    return 0;}


0 0
原创粉丝点击