• Luogu P5444 [APIO2019]奇怪装置


    题目
    这种题目看上去就是有循环节的对吧。
    在考场上,一个可行的方式是打表。
    现在我们手推一下这个循环节。
    记函数(f(t)=(((t+lfloorfrac tB floor)\%A),(t\%B))),那么(f(t_1)=f(t_2))的充要条件为:

    [t_1+lfloorfrac {t_1}B floorequiv t_2+lfloorfrac {t_2}B floor(mod A) ]

    [t_1equiv t_2(mod B) ]

    看到第二个很熟悉的式子,我们不妨设(t_2=t_1+xB(x>0)),代入第一个式子得到

    [t_1+lfloorfrac {t_1}B floorequiv t_1+xB+lfloorfrac {t_1+xB}B floor(mod A) ]

    后面那坨东西我们把它化简一下,拆开和左边的抵掉就变成了

    [xB+xequiv0(mod A) ]

    [A|x(B+1) ]

    (B+1)移到左边去

    [frac A{(A,B+1)}|x ]

    也就是说最小循环节为(xB=frac{AB}{(A,B+1)})
    剩下的做一个简单的区间覆盖即可。
    区间覆盖的话左端点升序排序,记录最大右端点即可。

    #include<bits/stdc++.h>
    #define ll long long
    using namespace std;
    namespace IO
    {
        char ibuf[(1<<21)+1],*iS,*iT;
        char Get(){return (iS==iT? (iT=(iS=ibuf)+fread(ibuf,1,(1<<21)+1,stdin),(iS==iT? EOF:*iS++)):*iS++);}
        ll read(){ll x=0;int c=Get();while(!isdigit(c))c=Get();while(isdigit(c))x=x*10+c-48,c=Get();return x;}
    }
    using namespace IO;
    const int N=1000007;
    struct node{ll l,r;}a[N<<1];
    int operator<(node a,node b){return a.l<b.l;}
    ll max(ll a,ll b){return a>b? a:b;}
    int main()
    {
        int n=read(),m=0,i;ll A=read(),B=read(),M=A/__gcd(A,B+1)*B,l,r,ans=0,mx=0;
        for(i=1;i<=n;++i)
        {
    	l=read(),r=read();
    	if(r-l+1>=M) return !printf("%lld",M);
    	l%=M,r%=M;
    	if(l>r) a[++m]=(node){0,r},a[++m]=(node){l,M-1}; else a[++m]=(node){l,r};
        }
        sort(a+1,a+m+1);
        for(i=1;i<=m;++i)
        {
    	if(a[i].l>mx) ans+=a[i].l-mx;
    	mx=max(mx,a[i].r+1);
        }
        if(mx<M) ans+=M-mx;
        return !printf("%lld",M-ans);
    }
    
  • 相关阅读:
    PHP学习笔记11——文件处理
    PHP学习笔记10——GD图片处理
    PHP学习笔记09——GD生成验证码实例
    PHP学习笔记08——GD绘图基础
    PHP学习笔记07——字符串和正则
    poj 3254 Corn Fields
    线程
    字符串是否包含问题
    左旋转字符串
    凸包问题
  • 原文地址:https://www.cnblogs.com/cjoierShiina-Mashiro/p/11644859.html
Copyright © 2020-2023  润新知