http://www.lydsy.com/JudgeOnline/problem.php?id=1026

Description

  windy定义了一种windy数。不含前导零且相邻两个数字之差至少为2的正整数被称为windy数。 windy想知道,
在A和B之间,包括A和B,总共有多少个windy数?

Input

  包含两个整数,A B。

Output

  一个整数

Sample Input

【输入样例一】
1 10
【输入样例二】
25 50

Sample Output

【输出样例一】
9
【输出样例二】
20

————————————————————————————————————

今天开始学数位dp了!

所以趁着这道题还简单赶紧记录下来。

设dp(n)表示0~n的windy数个数。

设f[i][j][0/1]表示当前处理到第i位数为j,此时前i位数比n的前i位数小于等于(为0)/大于(为1)的数的个数。

显然我们求a~b的个数可以利用前缀和,只需要求dp(b)再减去dp(a-1)即可。

那么对于函数dp(n),其主要流程:

1.将n拆成十进制数,存在数组中(这里数组为a,长度为len)

2.特殊处理第一层:

for(int i=;i<=;i++){
if(i<=a[])f[][i][]=;
else f[][i][]=;
}

3.枚举i=2~len层并处理之,枚举当前层填充的数字j和上一层填充数字k。当符合windy数的条件时开始更新,更新方程较显然就不多说了:

if(j<a[i])
f[i][j][]+=f[i-][k][]+f[i-][k][];
else if(j==a[i])
f[i][j][]+=f[i-][k][],f[i][j][]+=f[i-][k][];
else f[i][j][]+=f[i-][k][]+f[i-][k][];

4.得出答案。这里需要注意对于最后一层需要特殊处理防止越出0~n的范围。也很显然。

整套流程至此完毕,复杂度显然为log级别。

PS:判断是否为windy数很简单,这里用了一个辅助数组c[i][j]表示abs(i-j),借此判断能够美化代码(滑稽)

#include<cstdio>
#include<cstring>
using namespace std;
const int N=;
int a[N],f[N][N][],c[N][N];
int dp(int x){
int len=;
while(x)a[++len]=x%,x/=;
if(len==)a[++len]=;
memset(f,,sizeof(f));
for(int i=;i<=;i++){
if(i<=a[])f[][i][]=;
else f[][i][]=;
}
for(int i=;i<=len;i++){
for(int j=;j<=;j++){
for(int k=;k<=;k++){
if(c[j][k]>=){
if(j<a[i])
f[i][j][]+=f[i-][k][]+f[i-][k][];
else if(j==a[i])
f[i][j][]+=f[i-][k][],f[i][j][]+=f[i-][k][];
else f[i][j][]+=f[i-][k][]+f[i-][k][];
}
}
}
}
int ans=;
for(int i=;i<=a[len];i++)ans+=f[len][i][];
for(int i=len-;i;i--){
for(int j=;j<=;j++){
ans+=f[i][j][]+f[i][j][];
}
}
return ans;
}
int main(){
for(int i=;i<=;i++){
for(int j=i;j<=;j++){
c[i][j]=c[j][i]=j-i;
}
}
int a,b;
scanf("%d%d",&a,&b);
printf("%d\n",dp(b)-dp(a-));
return ;
}

BZOJ1026:[SCOI2009]windy数——题解的更多相关文章

  1. BZOJ1026 SCOI2009 windy数 【数位DP】

    BZOJ1026 SCOI2009 windy数 Description windy定义了一种windy数.不含前导零且相邻两个数字之差至少为2的正整数被称为windy数. windy想知道,在A和B ...

  2. bzoj1026: [SCOI2009]windy数(数位dp)

    1026: [SCOI2009]windy数 Time Limit: 1 Sec  Memory Limit: 162 MBSubmit: 8203  Solved: 3687[Submit][Sta ...

  3. bzoj1026: [SCOI2009]windy数(传说你是数位DP)

    1026: [SCOI2009]windy数 题目:传送门 题解: 其实之前年少无知的时候好像A过...表示当时并不知道什么数位DP 今天回来深造一发... 其实如果对这个算法稍有了解...看到这题的 ...

  4. BZOJ1026: [SCOI2009]windy数[数位DP]

    1026: [SCOI2009]windy数 Time Limit: 1 Sec  Memory Limit: 162 MBSubmit: 6346  Solved: 2831[Submit][Sta ...

  5. 【数位DP】bzoj1026: [SCOI2009]windy数

    1026: [SCOI2009]windy数 Time Limit: 1 Sec  Memory Limit: 162 MBSubmit: 4163  Solved: 1864[Submit][Sta ...

  6. 2018.06.30 BZOJ1026: [SCOI2009]windy数(数位dp)

    1026: [SCOI2009]windy数 Time Limit: 1 Sec Memory Limit: 162 MB Description windy定义了一种windy数.不含前导零且相邻两 ...

  7. bzoj千题计划117:bzoj1026: [SCOI2009]windy数

    http://www.lydsy.com/JudgeOnline/problem.php?id=1026 数位DP 如果前一位填的是0, 0是前导0,下一位可以随便填 0不是前导0,下一位不能填1 为 ...

  8. C++ 洛谷 P2657 [SCOI2009]windy数 题解

    P2657 [SCOI2009]windy数 同步数位DP 这题还是很简单的啦(差点没做出来 个位打表大佬请离开(包括记搜),我这里讲的是DP!!! 首先Cal(b+1)-Cal(a),大家都懂吧(算 ...

  9. [bzoj1026][SCOI2009]windy数_数位dp

    windy数 bzoj-1026 题目大意:求一段区间中的windy数个数. 注释:如果一个数任意相邻两位的差的绝对值都不小于2,这个数就是windy数,没有前导0.$区间边界<=2\cdot ...

随机推荐

  1. 使用duplicateweedout

    mysql> explain extended select * from cities where id in (select phonecode from countries group b ...

  2. Linux命令应用大词典-第32章 性能监控

    32.1 sar:收集.报告或保存系统活动信息 32.2 iostat:报告CPU统计数据和设备.分区输入.输出消息 32.3 iotop:进行I/O监控 32.4 mpstat:报告CPU相关的统计 ...

  3. hackerrank Project Euler #210: Obtuse Angled Triangles

    传送门 做出一个好几个星期屯下来的题目的感觉就是一个字: 爽! 上图的黄点部分就是我们需要求的点 两边的部分很好算 求圆的地方有一个优化,由于圆心是整数点,我们可以把圆分为下面几个部分,阴影部分最难算 ...

  4. C++11 type_traits 之is_convertible源码分析

    请看源码: struct __sfinae_types { typedef char __one; typedef ]; } __two; }; template<typename _From, ...

  5. Python基础 之 list类-列表

    list类-列表 一.list类的基本属性 1. 列表格式 li = [1, 12, 9, ", 10], "even"], "root", True ...

  6. Ubuntu14.04下部署FastDFS 5.08+Nginx 1.9.14

      最新的版本可以在这里获取,目前下载的最新版本是5.08,更新于2016-02-03.在这里可以找到更多的说明. 下载好后,server端分为两个部分,一个是tracker,一个是storage.顾 ...

  7. Fafa and the Gates(模拟)

    Two neighboring kingdoms decided to build a wall between them with some gates to enable the citizens ...

  8. android在程序崩溃时Catch异常并处理

    Android系统的"程序异常退出",给应用的用户体验造成不良影响.为了捕获应用运行时异常并给出友好提示,便可继承UncaughtExceptionHandler类来处理.通过Th ...

  9. Spring管理事务默认回滚的异常

    一.默认方式 Spring的事务管理默认只对出现运行期异常(java.lang.RuntimeException及其子类),Error进行回滚. 如果一个方法抛出Exception或者Checked异 ...

  10. 《剑指offer》---跳台阶问题

    本文算法使用python3实现 1. 问题1 1.1 题目描述:   一只青蛙一次可以跳上1级台阶,也可以跳上2级.求该青蛙跳上一个n级的台阶总共有多少种跳法.   时间限制:1s:空间限制:3276 ...