zoukankan      html  css  js  c++  java
  • 平时十七测

    题解:

    第一题:看数据范围是O(n),而且很像单调栈;

    如果不是环,维护一个单调递减的栈,弹栈的时候计算贡献,对于重复的元素,我们记一个size;

    环怎么办,显然是拆了,从最高的地方拆,那么就不可能有跨过他的元素,这样搞一遍单调栈就可以了;

    对于最高的元素再统计一下只有往外可以建边的贡献;

    #include<bits/stdc++.h>
    using namespace std;
    
    const int M = 5e6 + 10;
    int a[M], b[M], c[M];
    struct node{int cnt, w;}q[M];
    int read(){
        int x = 0; int f = 1; char c = getchar();
        while(c<'0'||c>'9'){if(c=='-')f=-1;c=getchar();}
        while(c<='9'&&c>='0'){x=x*10+c-'0';c=getchar();}
        return x*=f;
    }
    
    int main(){
        freopen("jolyne.in","r",stdin);
        freopen("jolyne.out","w",stdout);
        int n = read(), mx = 0;
        long long ans = 0;
        for(int i = 1; i <= n; i++) {
            b[i] = read();
            if(b[i] > b[mx]) mx = i; 
        }
        int y = 0;
        for(int i = mx; i <= n; i++)
            a[++y] = b[i];
        for(int i = 1; i < mx; i++)
            a[++y] = b[i];
        mx = a[n];
        memset(b, 0, sizeof(b));b[n]=1;
        for(int i = n - 1; i > 1; i--){
            b[i] = a[i] >= mx;
            mx = max(a[i], mx);
        }
        mx = a[2];c[2] = 1;
        for(int i = 3; i <= n; i++){
            c[i] = a[i] >= mx;
            mx = max(a[i], mx);
        }
        int h = 1, t = 0;
        for(int i = 1; i <= n; i++){
            while(h <= t && a[i] > q[t].w){
                ans += q[t].cnt;
                t--;
            }
            if(h <= t && q[t].w == a[i]){
                ans += q[t].cnt;
                q[t].cnt++;
                if(h != t) ans++;
                continue;
            }
            else if(h <= t)ans++; 
            q[++t] = (node) { 1, a[i] };
            //printf("%d %d
    ", i, ans);
        }
        for(int i = 1; i <= n; i++) ans += (b[i] && !c[i]);
        printf("%lld
    ", ans);
    }
    View Code

    第二题:DP, 这道题是一道思维题,如果一直想这个过程是怎么搞的,就GG了;

    f(i,0)代表第一次到第i号房间所用步数,f(i,1)代表第二次到达房间所用步数

    sum[i]:f[i][1]-f[i][0]的前缀和

    f[i][0] = f[i-1][1] + 1;

    f[i][1] = f[p[i]][1] - f[p[i]][0] + f[p[i]+1][1] - f[p[i]][0] + …… + f[i-1][1] - f[i-1][0] + f[i][0] + i - p[i] + 1 = sum[i-1] - sum[p[i] - 1] + f[i][0] + i - p[i] + 1;

    #include<bits/stdc++.h>
    using namespace std;
    const int M = 1000005;
    int a[M];
    #define ll long long
    ll f[M][2], sum[M];
    const ll mod = 1e9 + 7;
    
    int main(){
        freopen("rideon","r",stdin);
        freopen("rideon","w",stdout);
        int n;
        scanf("%d", &n);
        for(int i = 1; i <= n; i++) scanf("%d", &a[i]);
        f[1][0] = 0;
        f[1][1] = 1;
        sum[1] = 1;
           for(int i = 2; i <= n; i++)
        {
            f[i][0] = (f[i - 1][1] + 1)%mod;
            f[i][1] = ((f[i][0] + sum[i - 1]) % mod - sum[a[i] - 1] + i - a[i] + 1 + mod) % mod;
            sum[i] = (sum[i - 1] + f[i][1] - f[i][0]+mod)%mod;
            // cout <<i<<":"<< f[i][0] << " " << f[i][1] <<" "<<sum[i]<< endl;
        }
        ll ans = (f[n][1] + 1+mod)%mod;
        cout << ans<< endl;
    
    }
    View Code

    第三题:这道题很像AIRPORT,但是每次我都会忘记有一个叫拓扑的算法;

    #include<bits/stdc++.h>
    using namespace std;
    
    const int INF=1e9;
    const int N=5e5+10;
    const int M=2e6+10;
    int n,m,h,t,mn,ans;
    int du[M],qs[M],w[M];
    priority_queue<int>p,q; 
    
    struct Tst
    {
        int head[N],dis[N],du[N],tot;
    
        struct edge{int nxt, u, v;}G[M];
    
        inline void add(int x,int y){
            G[++tot].nxt = head[x]; head[x] = tot; G[tot].v = y; G[tot].u = x;
        }
        inline void clear(){
            tot = 0;
            memset(head, 0, sizeof(head));
            memset(du, 0, sizeof(du));
        }
    
        inline void solve(int S)
        {
            memset(dis,0,sizeof(dis));
            h=t=1;qs[1]=S;
            while(h<=t)
            {
                int x=qs[h++];
                for(int i=head[x];i;i=G[i].nxt)
                {
                    int y=G[i].v;
                    dis[y]=max(dis[y],dis[x]+1);
                    du[y]--;
                    if(!du[y])
                        qs[++t]=y;
                }
            }
        }
    };
    Tst A,B;
    
    inline void dele(int x)
    {
        q.push(x);
        while(!p.empty() && !q.empty() && q.top()==p.top())
        {
            q.pop();
            p.pop();
        }
    }
    
    int read(){
        int x = 0; int f = 1; char c = getchar();
        while(c<'0'||c>'9'){if(c=='-')f=-1;c=getchar();}
        while(c<='9'&&c>='0'){x=x*10+c-'0';c=getchar();}
        return x*=f;
    }
    void init(){
        A.clear();
        B.clear();
        memset(du, 0, sizeof(du));
        while(!q.empty())q.pop();
        while(!p.empty())p.pop();
    }
    
    
    int main()
    {
        freopen("johnny.in","r",stdin);
      freopen("johnny.out","w",stdout);
        int T;
        T = read();
        while(T--){
            init();
            n=read();m=read();
            for(int i=1;i<=m;++i)
            {
                int u,v;
                u=read();v=read();
                du[v]++;A.du[v]++;B.du[u]++;
                A.add(u,v);B.add(v,u);
            }
            for(int i=1;i<=n;++i)
            {
                du[i]++;du[n+1]++;
                A.du[i]++;A.du[n+1]++;
                B.du[i]++;B.du[0]++;
                A.add(0,i);A.add(i,n+1);
                B.add(i,0);B.add(n+1,i);
            }
            A.solve(0);B.solve(n+1);
        
            for(int i=1;i<=m+2*n;++i)
                w[i]=A.dis[A.G[i].u]+B.dis[A.G[i].v]-1;
        
            h=t=1;qs[1]=0;
            mn=INF;
            while(h<=t)
            {
                int x=qs[h++];
                for(int i=B.head[x];i;i=B.G[i].nxt)
                dele(w[i]);
                if(x!=0 && x!=n+1)
                {
                    int y=p.top();
                    if(y<mn)
                        mn=y,ans=x;
                    else if(mn==y)ans = min(ans, x);
                }
                for(int i=A.head[x];i;i=A.G[i].nxt)
                {
                    int y=A.G[i].v;
                    p.push(w[i]);
                    du[y]--;
                    if(!du[y])
                        qs[++t]=y;
                }
            }
            printf("%d %d
    ",ans,mn);    
        }
    
        
    
        return 0;
    }
    View Code
  • 相关阅读:
    commando VM安装
    Pocscan搭建详解
    Windows-RW-LinuxFS
    Festival
    ffmpeg-metadata
    FFmpeg-Screen-Recording
    ffmpeg-map
    ffmpeg-utils
    Linux-Fcitx5
    ffmpeg-volumedetect
  • 原文地址:https://www.cnblogs.com/EdSheeran/p/9867459.html
Copyright © 2011-2022 走看看