题目:给定范围,求这个范围内不含有4 和 62 的数字有多少个。
两种方法
第一种方法是dfs搜索,顺便记忆化一下,也是数位dp的模板
#include <iostream>
#include <cstdio>
#include <algorithm>
#include <cstring>
using namespace std;
int line[10];
int dp[10][2];
int dfs( int len, int pre,int flag )
{
if ( len==0 ) return 1; // 因为搜索的入口是满足条件的,所以return 1
if ( !flag && dp[len][pre]!=-1 ) return dp[len][pre];
int end = flag?line[len]:9;
int ans = 0;
for ( int i=0;i<=end;i++ )
{
if ( i!=4 && !( pre&&i==2) ) ans += dfs( len-1,i==6,flag&&i==end );
}
if ( !flag ) dp[len][pre] = ans;
return ans;
}
int solve( int x )
{
int t = x;
int len = 0;
while( t )
{
line[++len] = t%10;
t /= 10 ;
}
memset( dp,-1,sizeof dp );
return dfs( len ,0 ,1 ) ;
}
int main()
{
int r,l;
while( scanf("%d%d",&l,&r) )
{
if ( l==0 && r==0 ) break;
cout<<solve( r ) - solve( l-1 ) <<endl;
}
return 0;
}
找出来不吉利的数字,然后减掉,但是不会判断x是否满足条件
#include <iostream>
#include <cstdio>
#include <algorithm>
using namespace std;
int dp[10][3];
int a[10];
void init()
{
dp[0][0] = 1 ;
for ( int i=1; i<=8; i++ )
{
dp[i][0] = dp[i-1][0]*9 - dp[i-1][1] ; //i位不满足条件的
dp[i][1] = dp[i-1][0] ; //i位 不满足条件中 最高位是2 的
dp[i][2] = dp[i-1][0] + dp[i-1][1] + dp[i-1][2]*10; // 满足条件
}
}
int solve ( int x )
{
int cnt = 0 ;
int temp = x ,len =0 ;
while ( temp )
{
a[++len] = temp%10;
temp /=10;
}
a[ len+1 ] = 0 ;
int flag = 0 ;
for ( int i=len; i>=1; i-- )
{
cnt += a[i]*dp[i-1][2];
if ( flag ) {
cnt += dp[i-1][0]*a[i];
}
else {
if ( a[i]>4 ) cnt+=dp[i-1][0];
if ( a[i]>2 && a[i+1]==6 ) cnt+=dp[i][1];
if ( a[i]>6 ) cnt+=dp[i-1][1]; //!!
if ( a[i]==4 ||( a[i]==2 && a[i+1]==6 ) ) flag = 1;
}
}
return x-cnt ;
}
int main()
{
int n,m;
init();
while( scanf("%d%d",&m,&n) )
{
if ( m==0 && m==n ) break;
printf("%d\n",solve( n+1 ) - solve( m ) ) ;
}
return 0;
}
本文介绍了一种计算指定范围内不包含特定数字(如4和62)的有效方法。通过两种不同的算法实现:一种是基于深度优先搜索(DFS)的数位DP模板,另一种则是通过找出不满足条件的数字并从中减去的方法。这两种方法都能有效地解决该问题。
2027

被折叠的 条评论
为什么被折叠?



