• [BZOJ5064] [HDU3652] B-number 数位DP


    题目描述

    B数的定义:能被13整除且本身包含字符串"13"的数。

    例如:130和2613是B数,但是143和2639不是B数。

    你的任务是计算1到n之间有多少个数是B数。

    输入

    输入数据只有一个数,为n。((1<=N<=10^{15})

    输出

    输出数据包含一行,为1到n之间B数的个数。

    样例输入

    13
    

    样例输出

    1
    

    题解

    数位DP

    记录对13的模数来判断是否可以被13整除。

    同时记录是否出现过‘13’, 还要考虑首位前导0的情况。

    (f[i][j][k][0/1])(i)位数,对(13)取模结果为(j),首位为(k),是否包含(13)的数的个数。

    预处理(f)数组后进行数位DP。

    先填充位数不满的,再由高位向低位将此位不满的加入答案。

    转换询问区间为([1,n))则更易简单处理。

    code

    #include <iostream>
    #include <cstdio>
    using namespace std;
    typedef long long LL;
    LL n, b[17], f[17][13][10][2];
    void init() {
        b[0] = f[0][0][0][0] = 1;
        for(int i = 1;i <= 16;i ++) {
            b[i] = b[i-1] * 10;
            for(int j = 0;j < 13;j ++) {
                for(int k = 0;k <= 9;k ++) {
                    for(int l = 0;l <= 9;l ++) {
                        f[i][(j+k*b[i-1])%13][k][1||(k==1&&l==3)] += f[i-1][j][l][1];
                        f[i][(j+k*b[i-1])%13][k][0||(k==1&&l==3)] += f[i-1][j][l][0];
                    }
                }
            }
        }
    }
    
    int main() {
        init();
        while(cin >> n) {
            int x = n + 1;
            int pos , j, di = 1 , flag = 0;
            LL now = 0 , ans = 0;
            for(pos = 1 ; b[pos] <= x ; pos ++ )
                   for(j = 1 ; j < 10 ; j ++ )
                    ans += f[pos][0][j][1];
            for( ; pos ; pos -- ) {
                for(j = di ; j < x / b[pos - 1] % 10 ; j ++ )
                    ans += f[pos][(13 - now * b[pos] % 13) % 13][j][1] + (flag || (x / b[pos] % 10 == 1 && j == 3)) * f[pos][(13 - now * b[pos] % 13) % 13][j][0];
                now = (now * 10 + x / b[pos - 1] % 10) % 13 , di = 0;
                if(x / b[pos] % 10 == 1 && x / b[pos - 1] % 10 == 3) flag = 1;
            }
            cout << ans << endl;
        }
        return 0;
    }
    
  • 相关阅读:
    了解Android_09之GridView(网格视图)
    了解Android_08之ListView(列表视图)
    了解Android_07之ImageView与使用glide第三方库加载网络图片
    了解Android_06之CheckBox
    了解Android_05之RadioButton
    了解Android_04之EditText标签
    了解Android_03之Button标签
    了解Android_02之TextView标签
    了解Android_01之HelloWorld
    02_vue本地应用(v-text,v-html,v-on,v-show,v-if,v-bind,v-for,v-model)
  • 原文地址:https://www.cnblogs.com/Paranoid-LS/p/11343585.html
Copyright © 2020-2023  润新知