hdu4507
数位dp,终于守得云开见月明了。建议初学者先试试两道比较简单的hdu2089,hdu3555。
鸣谢:http://blog.csdn.net/acm_cxlove/article/details/8707084。
数位dp也是一种基于状态压缩、优化的动态规划。不同的是,它的压缩和优化往往基于数的一些特性。而数最基本的表现形式:a/b --- [a/b]、[a%b]。
这种dp才是体现一个人智慧的地方。(额外想为ACM竞赛的同学说两句,个人还是特别顶复旦出题的,至少它出的绝大部分题目都是可以自己通过大学以前的数学知识慢慢想到,而不是像某些学校的题目,只要听说过、学过、看过,某一个不知道哪里冒出来的数学理论就能瞬间AC,否则***。还是不放水了,言归正传)
本题,中文描述的,不解释了。初学者往往都会往容斥的方面想,(也不是不可以)但其实条件2、条件3的综合比较困难了,代码量和复杂度可能都会很大。
所以直接递归找跟7有关的数比较科学,假设原数字a+b位,如果搜索前a位fa(fa后b位都是0),后面b位跟7有关的任何一个数x,产生的结果和是(fa+x)^2+x^2。对所有的x,就有{fa^2*cnt(x)+2fa*sum(x)+sum(x^2)=f(a+b,b)}+f(b,0)。这个很容易想到,那么如果搜索时刚好按a从小到大拆分呢?不就是很明显了吗?
#include <iostream>
#include <cstring>
#include <cstdio>
#include <algorithm>
using namespace std;
#define LL long long
const LL mod = 1000000007LL;
#define mp(a,b) make_pair(a,b)
int bit[];
//长度,是否有7,数字和%7,数字%; 数字和、结果和、数字个数
long long s1[][][][],s2[][][][],cnt[][][][];
LL fac[]={};
typedef pair<pair<LL,LL>,LL> pll;
pll DP(int len,int a,int b,int c,int g){
//printf("len = %d, %d, %d, %d, g = %d\n",len,a,b,c,g);
if(g && cnt[len][a][b][c] >= )
return mp(mp(cnt[len][a][b][c],s1[len][a][b][c]),s2[len][a][b][c]);
if(len <= ){
if(b&&c&&!a) cnt[][a][b][c]=;
else cnt[][a][b][c]=;
s1[][a][b][c]=s2[][a][b][c]=;
return mp(mp(cnt[len][a][b][c],s1[len][a][b][c]),s2[len][a][b][c]);
}
int bound=bit[len]; if(g) bound=;
LL tcnt=,ts1=,ts2=;
int nl=len-,na,nb,nc;
for(int i=;i<=bound;i++){
na=(a||i==); nb=(b+i)%; nc=(c*+i)%;
pll p=DP(nl,na,nb,nc,g||(i<bound));
LL f = fac[nl]*i % mod; //f按位拆分,不用靠递归记录!!!
tcnt= (tcnt+p.first.first)%mod;
ts1 = (ts1+p.first.second+p.first.first*f)%mod;
ts2 = (ts2+p.first.first*(f*f%mod)%mod+p.first.second*f*%mod+p.second)%mod;
}
if(g){
cnt[len][a][b][c] = tcnt;
s1[len][a][b][c] = ts1;
s2[len][a][b][c] = ts2;
}
return mp(mp(tcnt,ts1),ts2);
}
LL sum(LL n){
LL a=n,b=n+,c=*n+;
LL x=,y=;
if(a%x==) a/=x,x=;if(a%y==) a/=y,y=;
if(b%x==) b/=x,x=;if(b%y==) b/=y,y=;
if(c%x==) c/=x,x=;if(c%y==) c/=y,y=;
a%=mod;b%=mod;c%=mod;
return (a*b%mod)*c%mod;
}
LL solve(LL n){
if(n <= ) return ;
int len=;
memset(bit,,sizeof(bit));
LL m=n;
while(n > )
bit[++len]=n%, n/=;
//cout<<"n = "<<m<<" ,len = "<<len<<endl;
return ((sum(m)-DP(len,,,,).second)%mod+mod)%mod;
}
int main()
{
for(int i=;i<;i++)
fac[i]=(fac[i-]*)%mod;
memset(cnt,-,sizeof(cnt));
int cases; cin>>cases;
for(int cas=;cas<=cases;cas++){
LL l,r;
cin>>l>>r;
//scanf("%lld%lld",&l,&r);
cout<<((solve(r)-solve(l-))%mod+mod)%mod<<endl;
}
return ;
}
hdu4507的更多相关文章
- [HDU4507]吉哥系列故事——恨7不成妻
[HDU4507]吉哥系列故事--恨7不成妻 试题描述 单身!依然单身!吉哥依然单身!DS级码农吉哥依然单身!所以,他生平最恨情人节,不管是214还是77,他都讨厌!吉哥观察了214和77这两个数,发 ...
- HDU-4507 吉哥系列故事——恨7不成妻 数位DP
题意:给定区间[L, R]求区间内与7无关数的平方和.一个数当满足三个规则之一则认为与7有关:1.整数中某一位是7:2.整数的每一位加起来的和是7的整数倍:3.这个整数是7的整数倍: 分析:初看起来确 ...
- hdu4507 数位dp+推公式
推公式的能力需要锻炼.. /* dp的时候要存结构体 里面三个元素: cnt,就是满足条件的个数 sum1,就是满足条件的数字和 sum2,满足条件的数字平方和 推导过程:还是用记忆化搜索模板 dp[ ...
- 【HDU4507】恨7不成妻
Description 单身! 依然单身! 吉哥依然单身! DS级码农吉哥依然单身! 所以,他生平最恨情人节,不管是214还是77,他都讨厌! 吉哥观察了214和77这两个数,发现: 2+1+4=7 ...
- hdu-4507 吉哥系列故事——恨7不成妻 数位DP 状态转移分析/极限取模
http://acm.hdu.edu.cn/showproblem.php?pid=4507 求[L,R]中不满足任意条件的数的平方和mod 1e9+7. 条件: 1.整数中某一位是7:2.整数的每一 ...
- 2018.09.27 hdu4507吉哥系列故事——恨7不成妻(数位dp)
传送门 一道比较综合的数位dp. 维护三个值:[L,R][L,R][L,R] 区间中与7无关的数的数量,与7无关的数之和,与7无关的数的的平方和. 然后可以用第一个值推第二个,第一个和第二个值推第三个 ...
- 【hdu4507】吉哥系列故事——恨7不成妻 数位dp
题目描述 求 $[L,R]$ 内满足:数位中不包含7.数位之和不是7的倍数.本身不是7的倍数 的所有数的平方和 mod $10^9+7$ . 输入 输入数据的第一行是case数T(1 <= T ...
- 【HDU4507】恨7不成妻(数位DP)
点此看题面 大致题意: 让你求出一段区间内与\(7\)无关的数的平方和.与\(7\)无关的数指整数中任意一位不为\(7\).整数的每一位加起来的和不是\(7\)的整数倍.这个整数不是\(7\)的倍数. ...
- hdu4507(数位DP)
题目意思: 给定一个区间,求这段区间中,不含7,对7取余为0,各个位数相加之和对7取余为0的数的平方和. 设d[i][j][k][m]代表长度为i的,对7取余为j的,各个位数相加之和对7取余为k的数的 ...
随机推荐
- Android 自己定义 TextView drawableTop 图标与文字左对齐(效果图)
public class DrawableTopLeftTextView extends TextView { private Paint mPaint; private float fFontHei ...
- 移植busybox-1.21.1
busybox官网:www.busybox.net 1.解压 # tar jxvf busybox-1.21.1.tar.bz2 2.配置 # cd busybox-1.21.1 # make men ...
- asp.net web api的自托管模式HttpSelfHostServer可以以控制台程序或windows服务程序为宿主,不单单依赖于IIS web服务器
Self-Hosting ASP.NET Web API http://theshravan.net/self-hosting-asp-net-web-api/ http://www.piotrwal ...
- Spark里面的任务调度:离SparkContext开始
SparkContext这是发达国家Spark入学申请,它负责的相互作用和整个集群,它涉及到创建RDD.accumulators and broadcast variables.理解力Spark架构, ...
- javascript中关于数组的迭代方法
//都接受3个参数,分别为:值.在数组中的位置.数组对象本身 var num = [2, 1, 5, 4, 2, 1, 6, 8, 19]; //every:若每一项都返回true,则返回true v ...
- jQuery--checkbox全选/取消全选
用JavaScript使页面上的一组checkbox全选/取消全选,逻辑很简单,实现代码也没有太难的语法.但使用jQuery实现则更简单,代码也很简洁,精辟! jQuery版本:1.3.2 <h ...
- 整理HTML的一些基础
HTML,超文本标记语言(HyperText Markup Language) 超文本:指页面内可以包含图片.链接.音乐.程序等非文字元素 标记:页面的由各种标签(标记)组成,文本有隐藏的文本标签 H ...
- UVA 1622 Robot
题意: 给出n*m个格子,每个格子里有一个机器人,可以执行东南西北四种指令,但是移动出格就会爆炸.给出四种指令的个数,求最多完成多少次指令. 分析: 首先对输入数据进行处理,使得cw≥ce.cn≥cs ...
- error: undefined reference to `XXX::XXX(type1, ypte2)
moc_fortunethread.cpp:100: error: undefined reference to `FortuneThread::GetToParentThread(QString, ...
- dev中 使用一些控件后,窗体屏蔽右键某些菜单
使用Ribbon时,ribbonControl1.ShowToolbarCustomizeItem=false; 使用LayoutControl时,layoutControl1.AllowCustom ...