Description:
windy定义了一种windy数。不含前导零且相邻两个数字之差至少为2的正整数被称为windy数。 windy想知道,
在A和B之间,包括A和B,总共有多少个windy数?
Input
包含两个整数,A B。
Output
一个整数
【输入样例一】
1 10
【输入样例二】
25 50
【输出样例一】
9
【输出样例二】
20
【数据规模和约定】
100%的数据,满足 1 <= A <= B <= 2000000000 。
抽空复习了一下数位DP。。。。感觉已经是一个嘴炮选手了。。。。各种细节问题。。
反正差不多就那个样子吧。。
#include<iostream>
#include<cstring>
#include<algorithm>
#include<stack>
#include<cstdio>
#include<queue>
#include<cstdlib>
#define LiangJiaJun main
#define INF 1999122700
using namespace std;
int a,b,f[24][24],base[24];
int DP(int n){
if(n == 0) return 0;
int now = 10 , x = 0, ans = 0 , last = 0;
while(base[now] > n) now --;
for(int i=1;i<now;i++)
for(int j=1;j<=9;j++) ans += f[i][j];
x = n / base[now];
for(int i=1;i<x;i++) ans += f[now][i];
n %= base[now];
last = x;
for(int i=now-1;i;i--){
x = n / base[i];
if(i != 1){
for(int j=0;j<x;j++) if(abs(last-j)>=2)ans += f[i][j];
}
else{
for(int j=0;j<=x;j++) if(abs(last-j)>=2)ans += f[i][j];
}
if(abs(x - last) < 2) break;
last = x;
n %= base[i];
}
return ans;
}
int LiangJiaJun(){
scanf("%d%d",&a,&b);
if(b <= 10) return printf("%d\n", b - a),0;
for(int i=0;i<=9;i++) f[1][i] = 1;
for(int i=2;i<=10;i++)
for(int j=0;j<=9;j++)
for(int k=0;k<=9;k++)if(abs(j-k) >= 2){
f[i][j] += f[i-1][k];
}
base[1]=1;
for(int i=2;i<=10;i++) base[i]=base[i-1]*10;
printf("%d\n",DP(b) - DP(a-1));
return 0;
}
更新:
有一种更好的数位DP写法,更加好写
#include<iostream>
#include<cstdio>
#include<cstring>
#include<cstdlib>
#include<cmath>
#include<algorithm>
#define LiangJiaJun main
#define ll long long
using namespace std;
ll f[14][14];
ll A,B;
int pre(){
for(int i=0;i<=9;i++)f[1][i]=1;
for(int i=1;i<=12;i++){
for(int j=0;j<=9;j++){
for(int k=0;k<=9;k++){
if(abs(j-k)>=2){
f[i][j]+=f[i-1][k];
}
}
}
}
return 0;
}
ll dp(ll x){
ll k=x,ans=0,a[14];
int len=0;
while(k){
a[++len]=k%10;
k/=10;
}
for(int i=1;i<len;i++){
for(int j=1;j<=9;j++){
ans+=f[i][j];
}
}
for(int i=1;i<a[len];i++)ans+=f[len][i];
for(int i=len-1;i>=1;i--){
for(int j=0;j<a[i];j++){
if(abs(a[i+1]-j)>=2)ans+=f[i][j];
}
if(abs(a[i+1]-a[i])<2)break;
}
return ans;
}
int w33ha(){
printf("%lld\n",dp(B+1)-dp(A));
return 0;
}
int LiangJiaJun(){
pre();
while(scanf("%lld%lld",&A,&B)!=EOF)w33ha();
return 0;
}