题解:P13085 [SCOI2009] windy 数(加强版)
LinkCatTree · · 题解
来水题解了。
由于
令
接下来考虑如何计算
假设我们要求小于等于一个数
最后考虑
总的来说,如果
计算
代码如下,仅供参考:
#include<bits/stdc++.h>
using namespace std;
typedef unsigned long long ull;
ull f[20][10],power[20];
void init() {
power[0]=1;
for(int i=1;i<=19;i++) power[i]=power[i-1]*10;
for(int i=0;i<=9;i++) f[1][i]=1;
for(int i=2;i<=19;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 ;
}
ull solve(ull x) {
int w=0,y,pre;
ull ans=0;
while(power[w]<=x) w++;
for(int i=1;i<w;i++)
for(int j=1;j<=9;j++)
ans+=f[i][j];
y=x/power[w-1];
for(int j=1;j<y;j++) ans+=f[w][j];
pre=y,x%=power[w-1];
for(int i=w-1;i>=1;i--) {
y=x/power[i-1];
for(int j=0;j<y;j++)
if(abs(j-pre)>=2)
ans+=f[i][j];
if(abs(pre-y)<2) break;
pre=y,x%=power[i-1];
}
return ans;
}
int main() {
ull a,b;
cin>>a>>b;
init();
cout<<solve(b+1)-solve(a)<<endl;
return 0;
}