数位dp

数位dp

数位dp是一种计数用的dp,一般就是要统计一个区间[le,ri]内满足一些条件数的个数。所谓数位dp,字面意思就是在数位上进行dp咯。数位还算是比较好听的名字,数位的含义:一个数有个位、十位、百位、千位…数的每一位就是数位啦!

之所以要引入数位的概念完全就是为了dp。数位dp的实质就是换一种暴力枚举的方式,使得新的枚举方式满足dp的性质,然后记忆化就可以了。

windy数

不含前导零且相邻两个数字之差至少为 2 的正整数被称为 windy 数。求a,b之间有几个windy数

输入格式
输入只有一行两个整数,分别表示 a和 b

输出格式
输出一行一个整数表示答案。

输入输出样例
输入
1 10
输出
9
输入
25 50
输出
20

#include<iostream>
using namespace std;

const int MAX = 10;
int dp[MAX][10];
int max[MAX];
int a, b;

int dfs(int pos, int pre,bool lead, bool flag)
{
	cout << pos << ' ' << pre << ' ' << lead << ' ' << flag << endl;
	if (pos == 0)
	{
		return 1;
	}
	if (!flag&&!lead&&dp[pos][pre] != -1)
		return dp[pos][pre];
	int max_num = (flag ? max[pos] : 9);
	cout << max_num << endl;
	int cnt = 0;
	for (int i = 0; i <= max_num; i++)
	{
		if (!lead&&abs(i - pre) < 2)
			continue;
		cnt += dfs(pos - 1, i, lead && (i == 0), flag && (i == max_num));
	}
	if (!lead&&!flag)dp[pos][pre] = cnt;
	return cnt;
}


int solve(int n)
{
	int pos = 0;
	while (n)
	{
		max[++pos] = n % 10;
		n /= 10;
	}
	memset(dp, -1, sizeof(dp));
	return dfs(pos, -1, true, true);
}

int main()
{
	cin >> a;

	cout << solve(a)<< endl;
	system("pause");
	return 0;
}
  • 0
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值