Topic link

Train of thought

Numnumnum = d1d2; numnumnum = d1d2; numnumnum = d1d2; dmd_1d_2… d_md1d2… Dm, denoted as leftleftLeft, then DMDM −1 is added to the right. d1d_md_{m-1}… D_1dmdm – 1… Let len=10^mlen=10 ^mlen=10m, let len=10^mlen=10 ^mlen=10m, let rateirate_iratei, For example, the rateraterate of 234234234 is 100010001000. Then the sum of the intervals after wrapping becomes:


i = L R a i l e n + r a t e i l e n l e f t + r i g h t = l e n i = L R a i + l e n l e f t i = L R r a t e i + n u m r i g h t \sum \limits_{i=L}^R a_i\cdot len+rate_i\cdot len\cdot left+right\\ =len\sum \limits_{i=L}^Ra_i+len\cdot left\sum \limits_{i=L}^Rrate_i+num\cdot right

We found that the rateraterate of all digits in the interval would become Rate ⋅ LenRate \cdot Lenrate ⋅ Len after operation. Therefore, the interval Rateraterate and could be maintained to realize marking.

In addition to maintain the interval left and right respectively add those numbers.

code

#include<bits/stdc++.h>
#define lc p<<1
#define rc p<<1|1
#definerep(i,st,ed) for(int i=st; i<=ed; ++i)
#definebl(u,i) for(int i=head[u]; i; i=e[i].nxt)
#define en puts("")
#define LLM LONG_LONG_MAX
#define LLm LONG_LONG_MIN
#define pii pair<ll,ll> 
typedef long long ll;
typedef double db;
using namespace std;
const ll INF=0x3f3f3f3f;
void read(a) {}
void OP(a) {}
void op(a) {}
template <typename T, typename. T2>inline void read(T &_, T2 &... oth)
{
    int__ =0; _ =0;
    char ch=getchar(a);while(!isdigit(ch))
    {
        if(ch==The '-') __ =1;
        ch=getchar(a); }while(isdigit(ch))
    {
        _=_*10+ch- 48;
        ch=getchar(a); } _ = __? - _ : _;read(oth...) ; }template <typename T>
void Out(T _)
{
    if(_ <0)
    {
        putchar(The '-'); _ = - _; }if(_ > =10)
       Out(_ /10);
    putchar(_ %10+'0');
}
template <typename T, typename. T2>inline void OP(T _, T2... oth)
{
	Out(_).putchar('\n');
	OP(oth...) ; }template <typename T, typename. T2>inline void op(T _, T2... oth)
{
	Out(_).putchar(' ');
	op(oth...) ; }/ * # # # # # # # # # # # # # # # # # # # # # # # # # # # # # # # # # * /
const ll N=1E5+10,P=1E9+7;
ll n,q;
ll sum[4*N],rate[4*N],L[4*N],R[4*N],taglen[4*N];
void update(ll p)
{
	sum[p]=(sum[lc]+sum[rc])%P;
	rate[p]=(rate[lc]+rate[rc])%P;
}
void build(ll p,ll l,ll r)
{
	taglen[p]=1;
	if(l==r)
	{
		rate[p]=1;
		return;
	}
	ll mid=(l+r)>>1;
	build(lc,l,mid);
	build(rc,mid+1,r);
	update(p);
}
void flag(ll p,ll l,ll r,ll left,ll right,ll len)
{
	ll num=r-l+1;
	sum[p]=((sum[p]*len%P+right*num%P)%P+rate[p]*len%P*left%P)%P;
	L[p]=(L[p]+taglen[p]*left%P)%P;
	R[p]=(R[p]*len%P+right)%P;
	rate[p]=rate[p]*len%P*len%P;
	taglen[p]=taglen[p]*len%P;
}
void flag_(ll p,ll l,ll r,ll left,ll right,ll len)
{
	ll num=r-l+1;
	sum[p]=((sum[p]*len%P+right*num%P)+rate[p]*left%P)%P;
	L[p]=(L[p]*len+left*taglen[p]%P*taglen[p]%P)%P;
	R[p]=(R[p]*len+right)%P;
	rate[p]=rate[p]*len%P*len%P;
	taglen[p]=taglen[p]*len%P;
}
void push_down(ll p,ll l,ll r)
{
	ll mid=(l+r)>>1;
	flag(lc,l,mid,L[p],R[p],taglen[p]);
	flag(rc,mid+1,r,L[p],R[p],taglen[p]);
	L[p]=R[p]=0;
	taglen[p]=1;
}
void modify(ll p,ll l,ll r,ll al,ll ar,ll val)
{
	if(al<=l && ar>=r)
	{
		flag(p,l,r,val,val,10);
		return;
	}
	if(taglen[p]! =1)
		push_down(p,l,r);
	ll mid=(l+r)>>1;
	if(al<=mid)
		modify(lc,l,mid,al,ar,val);
	if(ar>mid)
		modify(rc,mid+1,r,al,ar,val);
	update(p);
}
ll query(ll p,ll l,ll r,ll al,ll ar)
{
	if(al<=l && ar>=r)
		return sum[p];
	ll mid=(l+r)>>1,ret=0;
	if(taglen[p]! =1)
		push_down(p,l,r);
	if(al<=mid)
		ret=(ret+query(lc,l,mid,al,ar))%P;
	if(ar>mid)
		ret=(ret+query(rc,mid+1,r,al,ar))%P;
	return ret;
}
void print(a)
{
	rep(i,1,n)
		op(query(1.1,n,i,i));
	en;
}
void solve(a)
{
	read(n,q);
	rep(p,1.4*n)
		sum[p]=rate[p]=L[p]=R[p]=taglen[p]=0;
	build(1.1,n);
	char ty[100];
	ll l,r,d;
	while(q--)
	{
		scanf("%s",ty);
		if(ty[0] = ='w')
		{
			read(l,r,d);
			modify(1.1,n,l,r,d);
		}
		else
		{
			read(l,r);
			OP(query(1.1,n,l,r)); }}}int main(a)
{
	int _;
	cin>>_;
	ll cnt=0;
	while(_ --) {printf("Case %lld:\n",++cnt);
		solve();
	}
}
Copy the code