zoukankan      html  css  js  c++  java
  • Codeforces Round #541 (Div. 2)

    Codeforces Round #541 (Div. 2)

    确认过眼神,是div2的人

    a Sea Battle

    题意:

    将两个紧邻的矩形围起来需要的方块数
    周长+4

    b Draw

    题意:

    给定出现的分数,求最多可能出现的平局数
    计算((x_i:y_i) to (x_{i+1},y_{i+1}))可能出现的平局数,可包含一边,如左边,如果不一样,最后可特判右边是否为平局

    code

    #include <bits/stdc++.h>
    using namespace std;
    #define ll long long;
    #define inf 0x3f3f3f3f
    #define CL(a,b) memset(a,b,sizeof(a))
    #define sf(a) scanf("%d",&a)
    #define pr(a) printf("%d
    ",a)
    #define db(a) printf("db %d
    ",a)
    #define fr0(i,m) for(int i=0;i<m;i++)
    #define fr1(i,m) for(int i=1;i<=m;i++)
    const int maxn = 1e4 + 5;
    const int maxm = 1e6+5;
    //author:fridayfang
    //date:19 2月 23
    //global varibles
    
    int solve(int a1,int b1,int a2,int b2){
        //including a1:b1
        if(a1==b1&&a2==b2) return a2-a1;
        if(a1==b1) return min(a2,b2)-a1+1;
        else{
            int nex=max(a1,b1);
            if(min(a2,b2)<nex) return 0;
            if(a2==b2) return a2-nex;
            else return min(a2,b2)-nex+1;
        }
    
    }
    struct scor{
        int a,b;
    }sc[maxn];
    
    int n;
    int main(){
        sf(n);
        int a,b;
        //db(solve(0,0))
        fr1(i,n){
            sf(sc[i].a),sf(sc[i].b);
        }
        int ans=0;
        fr1(i,n){
            ans+=solve(sc[i-1].a,sc[i-1].b,sc[i].a,sc[i].b);
    
        }
        ans+=(sc[n].a==sc[n].b);
        pr(ans);
        
        
        return 0;
    }
    

    c Birthday

    题意:

    排列n个数使得(abs(a_{i+1}-a_i))的最大值最小化,包含(a_{n-1}-a_0)的情况
    构造的做:排序,从小到大一次从两边向中间放,即数组边缘小,数组中心大
    证明:
    假设排序后的结果为(a_0,a_1..a_i,a_{i+1}..a_{n-1}) ,显然我们的做法不会大于(max(a_{i+2}-a_i));
    下面只需证明,任何一种做法都不会小于(max(a_{i+2}-a_{i})) 盗用codeforce图进行证明:
    c

    要使其小于(a_{i+2}-a_{i})(a_{i+2})(a_i)之间必须有(a_{i+1}),同时(a_{i+2})右边一定是更大的,(a_i)左边一定是更小的,那么最左端和最右端就矛盾了.

    code

    #include <bits/stdc++.h>
    using namespace std;
    #define ll long long;
    #define inf 0x3f3f3f3f
    #define CL(a,b) memset(a,b,sizeof(a))
    #define sf(a) scanf("%d",&a)
    #define pr(a) printf("%d
    ",a)
    #define db(a) printf("db %d
    ",a)
    #define fr0(i,m) for(int i=0;i<m;i++)
    #define fr1(i,m) for(int i=1;i<=m;i++)
    const int maxn = 100 + 5;
    const int maxm = 1e6+5;
    //author:fridayfang
    //date:19 2月 23
    //global varibles
    int hei[maxn];
    int ans[maxn];
    int n;
    int main(){
        sf(n);
        for(int i=0;i<n;i++){
            sf(hei[i]);
        }
        sort(hei,hei+n);
        for(int i=0;i<n;i+=2){
            int a=i>>1;
            int b=n-1-a;
            ans[a]=hei[i];
            if(i+1<n) ans[b]=hei[i+1];
    
        }
        fr0(i,n){
            printf("%d ",ans[i]);
        }
        
        
        return 0;
    }
    

    D. Gourmet choice

    题意

    给出n个菜和m个菜之间的相互关系(>,<,=),问是否矛盾,不矛盾则给出最少需要的等级编号
    并查集缩点+有向无环图的最长路径(注意建图方式)

    code

    #include <bits/stdc++.h>
    using namespace std;
    #define ll long long;
    #define inf 0x3f3f3f3f
    #define CL(a,b) memset(a,b,sizeof(a))
    #define sf(a) scanf("%d",&a)
    #define sfs(a) scanf("%s",a);
    #define pr(a) printf("%d
    ",a)
    #define db(a) printf("db %d
    ",a)
    #define fr0(i,m) for(int i=0;i<m;i++)
    #define fr1(i,m) for(int i=1;i<=m;i++)
    const int maxn = 2e3 + 5;
    const int maxm = 1e6+5;
    //author:fridayfang
    //date:19 2月 23
    //global varibles
    //拓扑排序
    int fa[2010];
    int head[2010];
    int find(int u){
        return fa[u]==u?u:fa[u]=find(fa[u]);
    }
    void unio(int u,int v){
        int x=find(u),y=find(v);
        fa[x]=y;
    }
    char mp[1005][1005];
    int n,m;//n行
    struct edge{
        int u,v,nxt;
    }es[1000*1000+10];
    int deg[2010];
    int cnt;
    void add(int u,int v){
        es[cnt].u=u,es[cnt].v=v,es[cnt].nxt=head[u];
        head[u]=cnt;
        deg[v]++;
        cnt++;
    }
    int dp[2010];
    int vis[2010];
    int topo(){
        queue<int> q;
        for(int i=0;i<m+n;i++){
            if(find(i)==i&&deg[i]==0){
                q.push(i);
                dp[i]=1;
            }
        }
        while(!q.empty()){
            int tmp=q.front();
            q.pop();
            for(int t=head[tmp];t!=-1;t=es[t].nxt){
                int u=es[t].u,v=es[t].v;
                deg[v]--;
                if(!deg[v]) q.push(v);
                dp[v]=max(dp[v],dp[tmp]+1);
            }
        }
        //have cycle?
        for(int i=0;i<m+n;i++){
            if(find(i)==i&&deg[i]!=0){
                return 1;
            }
        }
        return 0;
    }
    int main(){
        sf(n),sf(m);
        for(int i=0;i<n+m;i++){
            fa[i]=i;
        }
        fr0(i,n){
            sfs(mp[i]);
            for(int j=0;j<m;j++){
                if(mp[i][j]=='='){
                    unio(i,j+n);
                }
            }
        }
        //合并完成
        //建图
        CL(head,-1);
        fr0(i,n){
            fr0(j,m){
                int x=find(i),y=find(j+n);
                //if(x==y&&mp[i][j]!='='){
                    //printf("No
    ");//防止自己成环
                    //return 0;
                //}
                if(mp[i][j]=='>'){
                    add(find(j+n),find(i));
                }
                else if(mp[i][j]=='<'){
                    add(find(i),find(j+n));
                }
            }
        }
        //topo序的存在性和最长路径
        int ans=topo();
        if(ans==1){
            printf("No
    ");
            return 0;
        }
        else{
            printf("Yes
    ");
            for(int i=0;i<n;i++){
                int x=find(i);
                printf("%d ",dp[x]);
            }
            printf("
    ");
            for(int j=0;j<m;j++){
                int x=find(j+n);
                printf("%d ",dp[x]);
            }
        }
    
        
        return 0;
    }
    

    F. Asya And Kittens

    题意

    从合并的顺序推出相邻顺序,(只有相邻的集合才能合并)
    并查集+模拟链表(自己写的是静态链表)
    每次合并将链表也及进行合并,因为合并意味着集合相邻,即这些元素相邻

    code

    #include <bits/stdc++.h>
    using namespace std;
    //author:fridayfang
    //date:19 2月 24
    //global varibles
    #define ll long long;
    #define inf 0x3f3f3f3f
    #define CL(a,b) memset(a,b,sizeof(a))
    #define sf(a) scanf("%d",&a)
    #define pr(a) printf("%d
    ",a)
    #define db(a) printf("db %d
    ",a)
    #define fr0(i,m) for(int i=0;i<m;i++)
    #define fr1(i,m) for(int i=1;i<=m;i++)
    const int maxn = 150000 + 5;
    const int maxm = 1e6+5;
    //模拟并查集+静态链表
    int nxt[maxn],tail[maxn];//nxt[]存储下一个元素
    //nxt[i]=0表示链表结束
    //tail[]维护边界
    int fa[maxn];//并查集
    int find(int u){
        return u==fa[u]?u:fa[u]=find(fa[u]);
    }
    void unio(int u,int v){
        int x=find(u),y=find(v);
        fa[x]=y;
    }
    
    int n;
    int main(){
        sf(n);
        for(int i=1;i<=n;i++){
            fa[i]=tail[i]=i;
        }
        int r;
        for(int i=1;i<n;i++){
            int u,v;
            sf(u),sf(v);
            int x=find(u),y=find(v);
            fa[x]=y;
            //y代表的链表扩张,合并
            nxt[tail[y]]=x;//y链表尾部静态指针指向x
            tail[y]=tail[x];//y的尾部成为x的尾部
        }
        r=find(1);
        //输出链表
        //for(int r=find(1);r!=0;r=nxt[r]){
            //printf("%d ",r);
        //}
        while(r!=0){
            printf("%d ",r);
            r=nxt[r];
        }
    
        
        return 0;
    }
    

    e题好复杂,g题不会做

  • 相关阅读:
    一个JS的问题,请帮下忙!
    开始练习VS2003了
    SQL查询结果的合并问题
    几个微软的好东西!
    对谷歌输入发的一点疑虑
    Visual studio 2005 sdk 安装引起的后果
    Socket协议测试:TPS偏低,和响应时间计算出来的TPS不相符的问题
    数据库索引失效
    挡板模拟器桩模块驱动模块
    nmon 监控结果
  • 原文地址:https://www.cnblogs.com/fridayfang/p/10426698.html
Copyright © 2011-2022 走看看