需要记录的信息有:做到了第几位,上一位的数字,是否随便填
记搜实现起来实在是方便,数位DP应该不会卡常数
#include<algorithm>
#include<iostream>
#include<cstring>
#include<cstdlib>
#include<cstdio>
#include<cmath>
using namespace std;
inline int rd(){
int ret=0,f=1;char c;
while(c=getchar(),!isdigit(c))f=c=='-'?-1:1;
while(isdigit(c))ret=ret*10+c-'0',c=getchar();
return ret*f;
}
#define space() putchar(' ')
#define nextline() putchar('
')
void pot(int x){if(!x)return;pot(x/10);putchar('0'+x%10);}
void out(int x){if(!x)putchar('0');if(x<0)putchar('-'),x=-x;pot(x);}
const int MAXN = 22;
int f[MAXN][MAXN];
int a[MAXN],top;
int dfs(int dp,int lst,bool lim){
if(dp==0)return 1;
if(!lim&&lst>=0&&f[dp][lst]!=-1)return f[dp][lst];
int ret=0,up=(lim?a[dp]:9),pos;
for(int i=0;i<=up;i++){
if(abs(i-lst)<2) continue;
pos=i;
if(i==0&&lst==-3) pos=-3;
ret+=dfs(dp-1,pos,lim&(i==up));
}
if(!lim&&lst>=0) f[dp][lst]=ret;
return ret;
}
int solve(int x){
top=0;
while(x){
a[++top]=x%10;
x/=10;
}
memset(f,-1,sizeof(f));
return dfs(top,-3,1);
}
int main(){
int L,R;
L=rd();R=rd();
out(solve(R)-solve(L-1));
return 0;
}