计蒜客 17118 Maximum Flow(2017 ACM-ICPC 亚洲区(西安赛区)网络赛 E)

来源:互联网 发布:sftp用的什么端口 编辑:程序博客网 时间:2024/05/19 03:46

题目链接:Maximum Flow

题目大意:给你一张图,第i个点和第j个点之间有一条容量为i^j的路,求最大流

题目思路:找规律,每一层之间的差值由规律,然后写一些恶心的模拟就好了

#include <map>#include <set>#include <cmath>#include <queue>#include <stack>#include <vector>#include <cstdio>#include <cstring>#include <cstdlib>#include <iostream>#include <algorithm>using namespace std;typedef long long ll;const ll mod=1000000007;ll a[70],b[70];ll sumlen[70],sumnum[70],sumtotalnum[70],Len[70];int main(){    a[0]=1;    ll l,len=2,n;    l=2;    for(ll i=1;i<=64;i++){        a[i] = a[i-1]*4;        a[i] = (a[i]+mod)%mod;    }    b[0]=0;    for(ll i=1;i<=64;i++){        b[i]=2*b[i-1]%mod+a[i-1];        b[i]%=mod;    }    Len[0] = 1;    sumlen[0] = 1;    sumnum[0] = 0;    sumtotalnum[0] = 1;    for(ll i = 1;i < 64;i++){        Len[i] = 2*Len[i-1];        sumlen[i] = sumlen[i-1]+Len[i];        sumnum[i] = (b[i]+a[i])%mod;        sumtotalnum[i] = (sumtotalnum[i-1]+sumnum[i])%mod;    }    while(scanf("%lld",&n)!=EOF){        n -= 2;        if(n == 0) {puts("1");continue;}        ll ceng = 0,ans = 0,k;        for(ll i = 0;i <= 63;i++){            if(n >= sumlen[i]&&n <= sumlen[i+1])            {ceng = i+1;ans = (ans+sumtotalnum[i])%mod;k = n-sumlen[i];break;}        }        ceng++;        while(ceng){            if(k >= Len[ceng-1]){                ans = (ans+a[ceng-1]+b[ceng-1])%mod;                k -= Len[ceng-1];            }            ceng--;        }        ans=(ans+n+1)%mod;        printf("%lld\n",(ans+mod)%mod);    }    return 0;}
阅读全文
0 0
原创粉丝点击