转载请注明出处,谢谢http://blog.csdn.net/ACM_cxlove?viewmode=contents    by---cxlove

题意:给出一个环,每个点是一个数字,取一个子串,使得拼接起来的数字是K的倍数。

由于K不大,暂且不考虑环的话,那么dp[i][j]表示以i结尾的,模K为j的有多少个子串。

那么sigma (dp[i][0])便是不考虑环的答案。

考虑环的话,不知道别人怎么写的,我感觉我的写法不是很复杂。

环和情况1 和n肯定是必选的,那么便是一个前缀为后缀,一个后缀为前缀拼接而成。

所以枚举某个前缀,求出前缀模K,那么枚举后缀模K的值,通过之前已经预处理过的dp值,便可以求出有多少个后缀满足为K的倍数。

但是这样可能后缀和前缀重叠了,所以我们枚举前缀的同时,依次记录后缀不同模值的个数。

随着前缀的增长,这些后缀都是和前缀重叠的。

#include <iostream>
#include <cstdio>
#include <cstring>
#include <map>
#include <vector>
#include <string>
#include <queue>
#include <cmath>
#include <algorithm>
#define lson step << 1
#define rson step << 1 | 1
#pragma comment(linker,"/STACK:102400000,102400000")
using namespace std;
typedef long long LL;
const int N = 50005;
const int M = 205;
int n , k , a[N] ,l[N];
int dp[2][M] , prefix[N] , fac[N << 2] , suffix[N];
int cnt[M];
int cal (int x) {
int cnt = 0;
while (x) x /= 10 , cnt ++;
return cnt;
}
int main () {
#ifndef ONLINE_JUDGE
freopen ("input.txt" , "r" , stdin);
// freopen ("output.txt" , "w" , stdout);
#endif
while (scanf ("%d %d" , &n , &k) != EOF) {
fac[0] = 1;
for (int i = 1 ; i <= (n << 2) ; i ++)
fac[i] = fac[i - 1] * 10 % k;
for (int i = 1 ; i <= n ; i ++) {
scanf ("%d" , &a[i]);
l[i] = cal (a[i]);
}
for (int i = 0 ; i < 2 ; i ++) {
for (int j = 0 ; j < k ; j ++)
dp[i][j] = 0;
}
dp[1][a[1] % k] = 1;
LL ans = dp[1][0];
for (int i = 2 ; i <= n ; i ++) {
for (int j = 0 ; j < k ; j ++)
dp[i & 1][j] = 0;
dp[i & 1][a[i] % k] ++;
for (int j = 0 ; j < k ; j ++) {
dp[i & 1][(j * fac[l[i]] + a[i]) %k] += dp[(i - 1) & 1][j];
}
ans += dp[i & 1][0];
}
prefix[0] = 0;suffix[n + 1] = 0;
for (int i = 1 ; i <= n ; i ++) {
prefix[i] = (prefix[i - 1] * fac[l[i]] + a[i]) % k;
}
int len = 0;
for (int i = n ; i >= 1 ; i --) {
suffix[i] = (a[i] * fac[len] + suffix[i + 1]) % k;
len += l[i];
}
len = 0;
for (int i = 0 ; i < k ; i ++)
cnt[i] = 0;
for (int i = 1 ; i <= n ; i ++) {
cnt[suffix[i]] ++;
len += l[i];
int p = prefix[i];
for (int j = 0 ; j < k ; j ++) {
if ((j * fac[len] + p) % k) continue;
ans += dp[n & 1][j] - cnt[j];
}
}
printf ("%I64d\n" , ans);
}
return 0;
}

HDU 4669 Mutiples on a circle (DP , 统计)的更多相关文章

  1. HDU 4669 Mutiples on a circle (2013多校7 1004题)

    Mutiples on a circle Time Limit: 3000/1000 MS (Java/Others)    Memory Limit: 65535/65535 K (Java/Oth ...

  2. HDU 4669 Mutiples on a circle 数位DP

    题目链接: http://acm.hdu.edu.cn/showproblem.php?pid=4669 考察对取模的的理解深不深刻啊,当然还有状态的设计····设d[i][j]表示以第i个数结尾,余 ...

  3. HDU 4669 Mutiples on a circle(环状DP)

    题目链接 这是最早看懂题意的一题,状态转移,挺好想..但是比赛时候,就是没有想到怎么去重,而且当时有些情况,也没注意到. 先预处理的dp[0]的情况,就是以p[0]为结尾的情况.之后D就行了,例如样例 ...

  4. HDU 4669 Mutiples on a circle 不知道该归为哪一类。

    题意:给你N个珠宝和一个K,每个珠宝上面都有数字,这个珠宝做成项链,把珠宝上的数字拼起来如果可以整除掉K,那么久说这个数字为wonderful value,问你有多少种方案可以组成WONDERFUL ...

  5. HDU 4669 Mutiples on a circle 动态规划

    参考了官方题解给的方法: 对于处理循环,官方给了一种很巧妙的方法: #include <cstdio> #include <cstring> #include <cstd ...

  6. HDU 4665 Mutiples on a circle (圆环DP)

    题意 N个数的圆环上有多少种方案可以使得选出来的一段数是K的倍数(N<=50000, K<=200, a[i]<=1000). 思路 多校第七场1004.圆上的DP--大脑太简单处理 ...

  7. HDU 1024 Max Sum Plus Plus --- dp+滚动数组

    HDU 1024 题目大意:给定m和n以及n个数,求n个数的m个连续子系列的最大值,要求子序列不想交. 解题思路:<1>动态规划,定义状态dp[i][j]表示序列前j个数的i段子序列的值, ...

  8. HDU 1231 最大连续子序列 --- 入门DP

    HDU 1231 题目大意以及解题思路见: HDU 1003题解,此题和HDU 1003只是记录的信息不同,处理完全相同. /* HDU 1231 最大连续子序列 --- 入门DP */ #inclu ...

  9. hdu 4778 Gems Fight! 博弈+状态dp+搜索

    作者:jostree 转载请注明出处 http://www.cnblogs.com/jostree/p/4102743.html 题目链接:hdu 4778 Gems Fight! 博弈+状态dp+搜 ...

随机推荐

  1. 【Maven】项目添加Maven类库依赖

    1.右击项目-->Maven-->EnableDependencyManagement,按步骤完成操作. 2.右击项目-->Properties-->DeploymentAss ...

  2. ActionBar开启Overlay Mode(覆盖模式)

    以下内容参考自Android官网http://developer.android.com/training/basics/actionbar/overlaying.html#EnableOverlay ...

  3. uboot: 理解uboot要看哪些书

    概览:

  4. currentStyle和getComputedStyle的兼容写法

    今天学习javascript的时候,教程中介绍了一种简单实现jQuery 中css()方法的写法 <!DOCTYPE html> <html lang="en"& ...

  5. ASP.NET MVC 5 学习教程:通过控制器访问模型的数据

    原文 ASP.NET MVC 5 学习教程:通过控制器访问模型的数据 起飞网 ASP.NET MVC 5 学习教程目录: 添加控制器 添加视图 修改视图和布局页 控制器传递数据给视图 添加模型 创建连 ...

  6. 引用 mkimage使用详解

    引用 鱼 的 mkimage使用详解  uboot源代码的tools/目录下有mkimage工具,这个工具可以用来制作不压缩或者压缩的多种可启动映象文件. mkimage在制作映象文件的时候,是在原来 ...

  7. android 从服务器上获取APK并下载安装

    简单的为新手做个分享.    网上有些资料,不过都是很零散,或是很乱的,有的人说看不懂.    一直有新手说 做到服务器更新APK时没有思路,这里做个简单的分享,希望有不同思路的可以讨论.     下 ...

  8. activity变成Dialog的样式设置

    1.属性解析 <item name="android:windowFrame">@null</item> :Dialog的windowFrame框为无< ...

  9. 解析stm32的时钟

    STM32 时钟系统  http://blog.chinaunix.net/uid-24219701-id-4081961.html STM32的时钟系统 ***   http://www.cnblo ...

  10. iOS 使用SBJSON创建和解析JSON

    原文地址:http://blog.csdn.net/gf771115/article/details/7718403 //创建JSON NSDictionary *dictonary = [[NSMu ...