AtCoder Grand Contest 015 solution to a problem

Portal

\(A\)

Found to achieve the maximum and minimum, then the middle of any of which can be represented

typedef long long ll;
int n,a,b;ll res;
int main(){
    scanf("%d%d%d",&n,&a,&b);
    if(a>b||n==1&&a!=b)return puts("0"),0;
    res=(a+b+1ll*(n-2)*b)-(a+b+1ll*(n-2)*a)+1;
    printf("%lld\n",res);
    return 0;
}

\(B\)

Were calculated need to take a number and log on to twice

typedef long long ll;
const int N=1e5+5;
char s[N];int n;ll res,sum;
int main(){
    scanf("%s",s+1),n=strlen(s+1);
    fp(i,1,n)sum+=(s[i]=='U'?n-i:i-1);
    res=(1ll*n*(n-1)-sum)*2+sum;
    printf("%lld\n",res);
    return 0;
}

\(C\)

Blue dots difficult to find something similar to a tree, then the communication block number is the total number of points minus the number of edges, respectively, to maintain just fine

//quming
#include<bits/stdc++.h>
#define R register
#define fp(i,a,b) for(R int i=(a),I=(b)+1;i<I;++i)
#define fd(i,a,b) for(R int i=(a),I=(b)-1;i>I;--i)
#define go(u) for(int i=head[u],v=e[i].v;i;i=e[i].nx,v=e[i].v)
template<class T>inline bool cmax(T&a,const T&b){return a<b?a=b,1:0;}
template<class T>inline bool cmin(T&a,const T&b){return a>b?a=b,1:0;}
using namespace std;
const int N=2005;
char mp[N][N];int r[N][N],c[N][N],s[N][N],n,m,q;
inline int qs(R int x,R int y,R int xx,R int yy){
    return s[xx][yy]-s[x-1][yy]-s[xx][y-1]+s[x-1][y-1];
}
inline int qr(R int x,R int y,R int xx,R int yy){
    return r[xx][yy]-r[x-1][yy]-r[xx][y-1]+r[x-1][y-1];
}
inline int qc(R int x,R int y,R int xx,R int yy){
    return c[xx][yy]-c[x-1][yy]-c[xx][y-1]+c[x-1][y-1];
}
int main(){
    scanf("%d%d%d",&n,&m,&q);
    fp(i,1,n){
        scanf("%s",mp[i]+1);
        fp(j,1,m)s[i][j]=(mp[i][j]=='1')+s[i-1][j]+s[i][j-1]-s[i-1][j-1];
    }
    fp(i,1,n)fp(j,1,m-1){
        r[i][j]=r[i-1][j]+r[i][j-1]-r[i-1][j-1]+(mp[i][j]=='1'&&mp[i][j+1]=='1');
    }
    fp(i,1,n-1)fp(j,1,m){
        c[i][j]=c[i-1][j]+c[i][j-1]-c[i-1][j-1]+(mp[i][j]=='1'&&mp[i+1][j]=='1');
    }
    for(R int x,y,xx,yy;q;--q){
        scanf("%d%d%d%d",&x,&y,&xx,&yy);
        printf("%d\n",qs(x,y,xx,yy)-qr(x,y,xx,yy-1)-qc(x,y,xx-1,yy));
    }
    return 0;
}

\(D\)

First, if \ (A = B \) the answer is \ (1 \) , so we assume that \ (B> A \)

Find the first \ (A, B \) different bit binary sense \ (r \) , then the front of the bits are not used can be deleted

We then divided into two sets number \ (X: [A, 2 ^ r), Y: [2 ^ r, B] \)

Set \ (K \) of \ (B \) the first is less than \ (R & lt \) and is \ (1 \) binary bits, there

  • Only \ (X-\) , indicative of \ ([A, R & lt ^ 2) \) (corresponding to the number of direct elections), and only the minimum number of these is shown (it can be expressed as \ (A \) , the maximum number of \ (2-R & lt ^. 1 \) )

  • Only \ (the Y \) can be shown and only \ ([R & lt ^ 2, R & lt ^ 2 + 2 ^ {-1}. 1 + K] \) (since each \ (2 ^ r + 2 ^ i \ ) (I \ Leq K) is necessarily present in the \ (the Y \) ) is

  • Simultaneously with \ (X-\) and \ (the Y \) , indicative of \ ([R & lt ^ 2 + A, R & lt + 2 ^ {-1}. 1] \) (direct elections \ (2 ^ r \) and a \ (X \) number in), and only shows these (ibid)

Then we add direct \ ([A, R & lt + 2 ^ {-1}. 1] \) , and then click sentence \ (2 ^ r + 2 ^ {k + 1} -1 \) and \ (2 ^ r + a \) size just fine

//quming
#include<bits/stdc++.h>
#define R register
#define fp(i,a,b) for(R int i=(a),I=(b)+1;i<I;++i)
#define fd(i,a,b) for(R int i=(a),I=(b)-1;i>I;--i)
#define go(u) for(int i=head[u],v=e[i].v;i;i=e[i].nx,v=e[i].v)
template<class T>inline bool cmax(T&a,const T&b){return a<b?a=b,1:0;}
template<class T>inline bool cmin(T&a,const T&b){return a>b?a=b,1:0;}
using namespace std;
typedef long long ll;
ll a,b,res;
int main(){
    scanf("%lld%lld",&a,&b);
    if(a==b)return puts("1"),0;
    R int r,k;
    for(r=59;(a>>r&1)==(b>>r&1);--r);
    a&=(1ll<<(r+1))-1,b&=(1ll<<(r+1))-1;
    res=(1ll<<(r+1))-a;
    for(k=r-1;(~k)&&(b>>k&1^1);--k);
    if(a>(1ll<<(k+1)))res-=a-(1ll<<(k+1));
    printf("%lld\n",res);
    return 0;
}

\(E\)

Is the kind of data structure should I do stupid people ......

Let me talk about the practice of the solution to a problem I say it

First, after a long enough time, the relative order according to the number of all definitely \ (V \) relative order after sorting, denoted \ (id_i \) represented by \ (V \) after sorting \ (I \) in a position

We assume at the outset only \ (i \) is selected, then for a \ (x_j <x_i \) and \ (v_j> v_i \) point \ (J \) , will certainly go through \ (i \) so that they have been selected, and press \ (v \) sort after all \ (i, j \) points will be selected between

We For each \ (I \) , calculate the maximum \ (id_j \) and \ (x_j <x_i \) , denoted as \ (r_i \) , then all \ ([id_i, id_ {r_i }] \) between the point will be selected. Similarly define \ (L_i \) . Easy to find \ (l, r \) are monotonically drop

Then the problem into a given \ (n-\) intervals and to ensure that the left and right end points monotonically falling, select a number of such covering \ ([1, n-] \) , then we remember \ (F_i \) represents \ ([1 , I] \) have been covered by the program number, the prefix can transfer and optimization

I practice in the back

//quming
#include<bits/stdc++.h>
#define R register
#define fp(i,a,b) for(R int i=(a),I=(b)+1;i<I;++i)
#define fd(i,a,b) for(R int i=(a),I=(b)-1;i>I;--i)
#define go(u) for(int i=head[u],v=e[i].v;i;i=e[i].nx,v=e[i].v)
template<class T>inline bool cmax(T&a,const T&b){return a<b?a=b,1:0;}
template<class T>inline bool cmin(T&a,const T&b){return a>b?a=b,1:0;}
using namespace std;
const int P=1e9+7;
inline void upd(R int &x,R int y){(x+=y)>=P?x-=P:0;}
inline int add(R int x,R int y){return x+y>=P?x+y-P:x+y;}
inline int dec(R int x,R int y){return x-y<0?x-y+P:x-y;}
inline int mul(R int x,R int y){return 1ll*x*y-1ll*x*y/P*P;}
int ksm(R int x,R int y){
    R int res=1;
    for(;y;y>>=1,x=mul(x,x))(y&1)?res=mul(res,x):0;
    return res;
}
const int N=2e5+5;
struct node{
    int x,v;
    inline bool operator <(const node &b)const{return x<b.x;}
}a[N];
int id[N],l[N],r[N],f[N],n;
inline bool cmp(const int &x,const int &y){return a[x].v<a[y].v;}
int main(){
    scanf("%d",&n);
    fp(i,1,n)scanf("%d%d",&a[i].x,&a[i].v),id[i]=i;
    sort(a+1,a+1+n),sort(id+1,id+1+n,cmp);
    fp(i,1,n)l[id[i]]=r[id[i]]=i;
    fp(i,2,n)cmax(r[i],r[i-1]);
    fd(i,n-1,1)cmin(l[i],l[i+1]);
    f[0]=1;
    for(R int i=1,j=0,sum=1;i<=n;++i){
        while(j<l[i]-1)sum=dec(sum,f[j++]);
        upd(f[r[i]],sum),upd(sum,sum);
    }
    printf("%d\n",f[n]);
    return 0;
}

First press \ (x \) sort, for a \ (i \) , if it is initially selected will surely be selected, otherwise, let \ (las \) and \ (nxt \) were selected in the previous and the latter is selected, set \ (L \) represents \ ([1, las] \ ) the maximum speed of all, \ (R & lt \) represents \ ([nxt, n] \ ) in all the minimum speed value, then the \ (I \) will not be selected if and only if \ (I \ in [L, R & lt] \) (that is neither from the foregoing that several catch cause it to be selected, it is impossible back to catch a number of leads that they have been selected)

We set \ (las_i \) means that when \ (I \) after the election, the maximum \ (J \) such that \ (J \) after being selected \ ([j + 1, i -1] \) This interval each number will be selected, you can half, when the judge sentenced the chairman about the tree on the line

Then set \ (f [i] \) represents \ (I \) must choose the number of programs, then the one selected may be \ ([las [i], i-1] \) any one of a number, prefix and optimization look like a

//quming
#include<bits/stdc++.h>
#define R register
#define fp(i,a,b) for(R int i=(a),I=(b)+1;i<I;++i)
#define fd(i,a,b) for(R int i=(a),I=(b)-1;i>I;--i)
#define go(u) for(int i=head[u],v=e[i].v;i;i=e[i].nx,v=e[i].v)
template<class T>inline bool cmax(T&a,const T&b){return a<b?a=b,1:0;}
template<class T>inline bool cmin(T&a,const T&b){return a>b?a=b,1:0;}
using namespace std;
const int P=1e9+7;
inline void upd(R int &x,R int y){(x+=y)>=P?x-=P:0;}
inline int add(R int x,R int y){return x+y>=P?x+y-P:x+y;}
inline int dec(R int x,R int y){return x-y<0?x-y+P:x-y;}
inline int mul(R int x,R int y){return 1ll*x*y-1ll*x*y/P*P;}
int ksm(R int x,R int y){
    R int res=1;
    for(;y;y>>=1,x=mul(x,x))(y&1)?res=mul(res,x):0;
    return res;
}
inline int max(R int x,R int y){return x>y?x:y;}
inline int min(R int x,R int y){return x<y?x:y;}
const int N=2e5+5,M=N*35,inf=0x3f3f3f3f;
int ls[M],rs[M],sz[M],rt[N],nd;
void ins(int &p,int q,int l,int r,int x){
    p=++nd,ls[p]=ls[q],rs[p]=rs[q],sz[p]=sz[q]+1;
    if(l==r)return;int mid=(l+r)>>1;
    x<=mid?ins(ls[p],ls[q],l,mid,x):ins(rs[p],rs[q],mid+1,r,x);
}
int query(int p,int q,int l,int r,int ql,int qr){
    if(!(sz[p]-sz[q])||ql<=l&&qr>=r)return sz[p]-sz[q];
    int mid=(l+r)>>1,res=0;
    if(ql<=mid&&query(ls[p],ls[q],l,mid,ql,qr))return 1;
    if(qr>mid&&query(rs[p],rs[q],mid+1,r,ql,qr))return 1;
    return 0;
}
struct node{
    int x,v;
    inline bool operator <(const node &b)const{return x<b.x;}
}a[N];
int b[N],las[N],f[N],mx[N],mn[N],sum[N];
int n;
inline int find(R int pos){
    R int l=0,r=pos-1,ans=pos-1,mid;
    while(l<=r){
        mid=(l+r)>>1;
        if(mid==pos-1||mx[mid]+1>mn[pos]-1||!query(rt[pos-1],rt[mid],1,n,mx[mid]+1,mn[pos]-1))
            ans=mid,r=mid-1;
        else l=mid+1;
    }
    return ans;
}
int main(){
//  freopen("testdata.in","r",stdin);
    scanf("%d",&n);
    fp(i,1,n)scanf("%d%d",&a[i].x,&a[i].v),b[i]=a[i].v;
    sort(a+1,a+1+n),sort(b+1,b+1+n);
    fp(i,1,n){
        a[i].v=lower_bound(b+1,b+1+n,a[i].v)-b;
        ins(rt[i],rt[i-1],1,n,a[i].v);
    }
    mx[0]=0;fp(i,1,n)mx[i]=max(mx[i-1],a[i].v);
    mn[n+1]=inf;fd(i,n,1)mn[i]=min(mn[i+1],a[i].v);
    fp(i,1,n+1)las[i]=find(i);
    f[0]=sum[0]=1;
    fp(i,1,n+1){
        f[i]=dec(sum[i-1],(las[i]?sum[las[i]-1]:0));
        sum[i]=add(sum[i-1],f[i]);
    }
    printf("%d\n",f[n+1]);
    return 0;
}

\(F\)

Conclusion immortal title

The following set \ (f (x, y) \) represents \ (x, y \) number of steps removed and divided by the default \ (x <y \)

We first consider the Fibonacci number, and define the \ (F. [0] = F. [. 1] =. 1 \) , easy to find \ (f (F [i] , F [i + 1]) = i \) and for all \ (F (A, B) = I \) , there are \ (A \ GEQ F. [I], B \ GEQ F. [I +. 1] \) . So the first question is very simple to get out

We define a number of \ (f (a, b) \) is good if and only if the absence \ (c <a, d < b \) and \ (f (c, d) > f (a, b) \) , then the answer would only contribute to a good number of

We define a number of \ (f (a, b) \) is excellent, if and only if if \ (F (A, B) = K \) , then \ (a, b \ leq F [k + 2 ] + F [k-1] \)

One conclusion: any time after a good number of the removed through the division will become a good number of

Consider contradiction, assuming \ (A = Y, X B = Py + \) , and \ (F (A, B) = K +. 1 \) , then removed after division becomes \ ((x, y) \ ) If \ ((x, y) \ ) is not a good number of pairs, the \ (Y> F. [K + 2] + F. [. 1-K] \) , thereby

\[ \begin{aligned} &a=y>F[k+2]\\ &x>F[k]\\ &b=py+x\geq y+x>F[k+2]+F[k-1]+F[k]=F[k+3]\\ \end{aligned} \]

There \ (C = F. [K + 2], D = F. [K +. 3] \) , so \ (F (C, D)> F (A, B) \) , which \ ((a, b) \) is a good number of discrepancies

So we proved that any time a good number of the removed after the division will become after a number of excellent, and the number of excellent and not too much (said to meet \ (f (a, b) = k \ ) the number of outstanding number is \ (O (k) \) ? but I do not prove)

Then we hit the table all \ (f (a, b) = k \) of the outstanding number of sparring come out just fine, when asked to go with a good number to generate a good number of

//quming
#include<bits/stdc++.h>
#define R register
#define pb emplace_back
#define fp(i,a,b) for(R int i=(a),I=(b)+1;i<I;++i)
#define fd(i,a,b) for(R int i=(a),I=(b)-1;i>I;--i)
#define go(u) for(int i=head[u],v=e[i].v;i;i=e[i].nx,v=e[i].v)
template<class T>inline bool cmax(T&a,const T&b){return a<b?a=b,1:0;}
template<class T>inline bool cmin(T&a,const T&b){return a>b?a=b,1:0;}
using namespace std;
const int P=1e9+7;
inline void upd(R int &x,R int y){(x+=y)>=P?x-=P:0;}
inline int add(R int x,R int y){return x+y>=P?x+y-P:x+y;}
inline int dec(R int x,R int y){return x-y<0?x-y+P:x-y;}
inline int mul(R int x,R int y){return 1ll*x*y-1ll*x*y/P*P;}
int ksm(R int x,R int y){
    R int res=1;
    for(;y;y>>=1,x=mul(x,x))(y&1)?res=mul(res,x):0;
    return res;
}
typedef long long ll;
const int N=105,M=90;
struct node{
    ll x,y;
    inline node(R ll xx,R ll yy):x(xx),y(yy){}
};vector<node>g[N];
ll f[N],n,m,T,res,cnt;
int main(){
    f[0]=f[1]=1;fp(i,2,M)f[i]=f[i-1]+f[i-2];
    g[1].pb(node(1,2)),g[1].pb(node(1,3)),g[1].pb(node(1,4));
    fp(i,1,M-3){
        for(auto v:g[i]){
            R ll x=v.y,y=v.x+x;
            while(y<=f[i+3]+f[i])g[i+1].pb(node(x,y)),y+=x;
        }
    }
    scanf("%lld",&T);
    while(T--){
        scanf("%lld%lld",&n,&m);if(n>m)swap(n,m);
        for(cnt=1;f[cnt+1]<=n&&f[cnt+2]<=m;++cnt);
        if(cnt==1){printf("%lld %lld\n",cnt,n*m%P);continue;}
        res=0;
        for(auto v:g[cnt-1]){
            R ll x=v.x,y=v.y;
            if(y<=n)res+=(m-x)/y%P;
            if(y<=m)res+=(n-x)/y%P;
            res%=P;
        }
        printf("%lld %lld\n",cnt,res);
    }
    return 0;
}

Guess you like

Origin www.cnblogs.com/yuanquming/p/11561324.html