zoukankan      html  css  js  c++  java
  • windy数(数位dp)

    https://www.luogu.com.cn/blog/virus2017/shuweidp
    https://www.luogu.com.cn/problem/P2657

    #include <iostream>
    #include <cstdio>
    #include <cstring>
    #include <algorithm>
    using namespace std;
    #define ll long long
    const int maxn = 200100;
    
    ll dp[20][10];   //dp[i][j]为当前在 i 位,前一位的数是 j 时的方案数。
    ll num[20];
    
    ll dfs(int n,bool lead,bool limit,int pre)   //当前位  前导0标记 位限制 前一位数 
    {
        if(n<0) return 1;
        if(!limit && !lead && dp[n][pre]!=-1) return dp[n][pre];
        ll ans=0;
        int up=limit?num[n]:9;
        for(int i=0;i<=up;i++)
        {
            if(!lead &&abs(pre-i)<2)    continue;     //无前导0,并且相邻两数小于2 直接遍历下一个
            ans+=dfs(n-1,lead&&i==0,limit&&i==up,i);  //有前导0标记并且当前遍历位为0,前导0传递下去
        }                                             //有限制标志并且当前遍历位到了最大值,传递限制
        if(!limit&&!lead) dp[n][pre]=ans;         //无限制,记忆化
        return ans;
    } 
    
    ll solve(ll n)
    {
        int len=0;
        while(n)
        {
            num[len++]=n%10;
            n/=10;
        }
        return dfs(len-1,1,1,0);
    }
    
    int main()
    {
        ll a,b;
        memset(dp,-1,sizeof(dp));
        while(scanf("%lld%lld",&a,&b)!=EOF)
        {
            printf("%lld
    ",solve(b)-solve(a-1));
        }
        return 0;
    }
    
  • 相关阅读:
    5
    4
    2
    3
    1
    IOS js交互
    vm安装mac
    索引
    ORM 基础
    reids 日志no
  • 原文地址:https://www.cnblogs.com/chilkings/p/11979273.html
Copyright © 2011-2022 走看看