Acwing 1083. Windy数

Posted Jozky86

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了Acwing 1083. Windy数相关的知识,希望对你有一定的参考价值。

Acwing 1083. Windy数

题意:

Windy 定义了一种 Windy 数:不含前导零且相邻两个数字之差至少为 2 的正整数被称为 Windy 数。

Windy 想知道,在 A 和 B 之间,包括 A 和 B,总共有多少个 Windy 数?

题解:

和这个题没啥区别Acwing 1082. 数字游戏题解连接

代码:

#include<bits/stdc++.h>
#define debug(a,b) printf("%s = %d\\n",a,b);
typedef long long ll;
using namespace std;

inline int read(){
   int s=0,w=1;
   char ch=getchar();
   while(ch<'0'||ch>'9'){if(ch=='-')w=-1;ch=getchar();}
   while(ch>='0'&&ch<='9') s=s*10+ch-'0',ch=getchar();//s=(s<<3)+(s<<1)+(ch^48);
   return s*w;
}
const int maxn=15;
int f[maxn][maxn];
void init(){//这里求的是包含前导0的情况 
	for(int i=0;i<=9;i++)f[1][i]=1;
	
	for(int i=2;i<maxn;i++){
		for(int j=0;j<=9;j++){
			for(int k=0;k<=9;k++){
				if(abs(k-j)>=2){
					f[i][j]+=f[i-1][k];
				}
			}
		}
	}
}
int solve(int n){
	if(!n)return 0;
	vector<int>vec;
	while(n)vec.push_back(n%10),n/=10;
	int tot=0;
	int last=-1;
	//n位数的答案
	for(int i=vec.size()-1;i>=0;i--){
		int x=vec[i];
		for(int j=(i==vec.size()-1);j<x;j++){
			
			if(abs(j-last)>=2){
				tot+=f[i+1][j];
			}
		}
		if(abs(x-last)<2)break;
		last=x;
		if(!i)tot++;
	}

	//低于n位数 
	for(int i=1;i<=vec.size()-1;i++)
		for(int j=1;j<=9;j++)
			tot+=f[i][j];
	return tot;
} 
int main()
{
	int l,r;
	init();
	cin>>l>>r;
	cout<<solve(r)-solve(l-1);
	return 0;
}

以上是关于Acwing 1083. Windy数的主要内容,如果未能解决你的问题,请参考以下文章

P2657 [SCOI2009]windy数

[SCOI2009]windy数

「SCOI2009」windy数

[SCOI2009]windy数

BZOJ1026: [SCOI2009]windy数 ( 数位dp )

windy数