这道题是开始思路错了….然后看了kuangbin巨巨的blog,但是感觉看不懂….所以找了其他blog很久才略懂一些
题意:中文题…
思路:
这里我们举个例子是L=111,R=113,恩
解释一下最后一个式子,就是求平方和的
答案就是111^2+112^2+113^2,然后我们枚举每一位的话,我们要把一个数拆开
比如113这个数,我们dfs完了后边的13,我们看回到100的时候怎么处理
就是100+13,113^2=(1* 100+13)^2
=1* 1* 100* 100* tmp.cnt(有多少种情况当前位置是1)+(1* 100* 13)*2+13^2
=i* i* p[pos]* p[pos]* tmp.cnt+(i* p[pos]* tmp.sum)*2+tmp.sqsum
感觉解释的比较清楚了
第二步的式子代码中有解释,OVER
为了以防表达能力太弱还是给几个链接....
http://www.tuicool.com/articles/z2uQri
http://fszxwfy.blog.163.com/blog/static/44019308201332761933868/
http://blog.youkuaiyun.com/acm_cxlove/article/details/8707084
我就是结合了上边三个的blog才看懂的
#include<map>
#include<set>
#include<queue>
#include<stack>
#include<math.h>
#include<string>
#include<vector>
#include<stdio.h>
#include<string.h>
#include<iostream>
#include<algorithm>
using namespace std;
typedef long long LL;
#define maxn 1005
#define f(x) (x*1.0)
#define inf 0x3f3f3f3f
#define maxm maxn*maxn
#define min(a,b) (a>b?b:a)
#define max(a,b) (a>b?a:b)
#define lowbit(x) (x&(-x))
#define cheak(i) printf("%d ",i)
#define lson(x) (splay[x].son[0])
#define rson(x) (splay[x].son[1])
#define rfor(i,a,b) for(i=a;i<=b;++i)
#define lfor(i,a,b) for(i=a;i>=b;--i)
#define mem(a,b) memset(a,b,sizeof(a))
#define mec(a,b) memcpy(a,b,sizeof(b))
const LL mod=1e9+7;
int A[50];
struct node
{
LL cnt,sum,sqsum;
void init()
{
cnt=sum=sqsum=0;
}
}dp[20][10][10];
LL p[20];
//1 数中有7
//2 数位和是7的倍数
//3 数是7的倍数
node dfs(int pos,int Mod,int sum,bool edge)
{
if(pos==-1)
{
node tmp;
tmp.cnt=Mod!=0&&sum!=0;
tmp.sum=tmp.sqsum=0;
return tmp;
}
if(!edge&&dp[pos][Mod][sum].cnt!=-1)
return dp[pos][Mod][sum];
int end=edge?A[pos]:9;
int i;
node ans,tmp;
ans.init();
rfor(i,0,end)
if(i!=7)
{
tmp=dfs(pos-1,(Mod+i)%7,(sum*10+i)%7,edge&&i==end);
ans.cnt+=tmp.cnt;
ans.cnt%=mod;
//这个...就不用解释了...
ans.sum+=(tmp.sum+(p[pos]*i)%mod*tmp.cnt%mod)%mod;
//这个式子能拆成两部分
//1.tmp.sum是代表后边pos-1,pos-2....0的位数的和
//2. (p[pos]*i)*tmp.cnt是在这个位数是当前这个值得时候有tmp.cnt种情况
//所以只针对当前位数
ans.sum%=mod;
ans.sqsum+=(tmp.sqsum+(2*p[pos]*i)%mod*tmp.sum)%mod;
ans.sqsum%mod;
ans.sqsum+=((tmp.cnt*p[pos])%mod*p[pos]%mod*i*i%mod);
ans.sqsum%mod;
}
if(!edge) dp[pos][Mod][sum]=ans;
return ans;
}
long long solve(long long n)
{
int pos=0;
while(n)
{
A[pos++]=n%10;
n/=10;
}
return dfs(pos-1,0,0,1).sqsum;
}
int main()
{
int T,i,j,k;
LL l,r;
rfor(i,0,19)
rfor(j,0,6)
rfor(k,0,6)
dp[i][j][k].cnt=-1;
p[0]=1;
rfor(i,1,19) p[i]=p[i-1]*10%mod;
scanf("%d",&T);
while(T--)
{
scanf("%lld%lld",&l,&r);
LL ans=solve(r)-solve(l-1);
ans=(ans%mod+mod)%mod;
printf("%lld\n",ans);
}
return 0;
}