• 2019牛客多校第6场


    比赛总结

    @lfw 不要总是比赛吹水,想好了就赶快写,不然导致后面还有会写的题没时间写

    这场暴力出奇迹,G题n!*len完全不虚

    题解

    比赛链接:https://ac.nowcoder.com/acm/contest/886#question

    A Garbage Classification

     1 #include<bits/stdc++.h>
     2 using namespace std;
     3 int val[30];
     4 char ty[30];
     5 char s[2005];
     6 int main()
     7 {
     8     int t;
     9     scanf("%d",&t);
    10     for(int kace=1;kace<=t;kace++)
    11     {
    12         scanf("%s",s);
    13         scanf("%s",ty);
    14         int len=strlen(s);
    15         int cntd=0,cntw=0,cnth=0;
    16         for(int i=0;i<len;i++)
    17         {
    18             char c=ty[s[i]-'a'];
    19             if(c=='d') cntd++;
    20             if(c=='w') cntw++;
    21             if(c=='h') cnth++;
    22         }
    23         printf("Case #%d: ",kace);
    24         if(cnth*4>=len) puts("Harmful");
    25         else if(cnth*10<=len) puts("Recyclable");
    26         else if(cntd>=cntw*2) puts("Dry");
    27         else puts("Wet");
    28     }
    29 }
    View Code

    B Shorten IPv6 Address

    模拟题

      1 #include<bits/stdc++.h>
      2 #define maxl 1010
      3 using namespace std;
      4 
      5 int len,cas,anslen,tmplen;
      6 int slen[10],mi[5];
      7 char s[10][10],c[17];
      8 char ch[maxl],ans[maxl],tmp[maxl];
      9 
     10 inline void prework()
     11 {
     12     scanf("%s",ch+1);
     13     for(int i=1;i<=8;i++)
     14         slen[i]=0;
     15     for(int i=1;i<=8;i++)
     16     {
     17         for(int j=4;j>=1;j--)
     18         {
     19             int cc=0,id;
     20             for(int k=1;k<=4;k++)
     21             {
     22                 id=(i-1)*16+(j-1)*4+k;
     23                 if(ch[id]=='1')
     24                     cc+=mi[k];
     25             }
     26             s[i][++slen[i]]=c[cc];
     27         }
     28         while(s[i][slen[i]]=='0' && slen[i]>1)
     29             slen[i]--;
     30     }
     31 }
     32 
     33 inline bool jug()
     34 {
     35     for(int i=1;i<=tmplen;i++)
     36     if(tmp[i]<ans[i])
     37         return true;
     38     else if(tmp[i]>ans[i])
     39         return false;
     40     return false;
     41 }
     42 
     43 inline void mainwork()
     44 {
     45     anslen=128;int nxt;bool flag;
     46     for(int i=1;i<=8;i++)
     47     {
     48         tmplen=0;
     49         for(int j=1;j<i;j++)
     50         {
     51             for(int k=slen[j];k>=1;k--)
     52                 tmp[++tmplen]=s[j][k];
     53             tmp[++tmplen]=':';
     54         }
     55         nxt=i;
     56         while(slen[nxt]==1 && s[nxt][1]=='0' && nxt<=8)
     57             nxt++;
     58         if(nxt>=i+2)
     59         {
     60             if(tmplen>1)
     61                 tmp[++tmplen]=':';
     62             else
     63                 tmp[++tmplen]=':',tmp[++tmplen]=':';
     64         }
     65         else if(nxt==i+1)
     66         {
     67             tmp[++tmplen]='0';
     68             if(i<8)
     69                 tmp[++tmplen]=':';
     70         }
     71         for(int j=nxt;j<=8;j++)
     72         {
     73             for(int k=slen[j];k>=1;k--)
     74                 tmp[++tmplen]=s[j][k];
     75             if(j<8)
     76                 tmp[++tmplen]=':';
     77         }
     78         if(tmplen<anslen)
     79         {
     80             anslen=tmplen;
     81             for(int j=1;j<=tmplen;j++)
     82                 ans[j]=tmp[j];
     83         }
     84         else if(tmplen==anslen)
     85         {
     86             if(jug())
     87                 for(int j=1;j<=tmplen;j++)
     88                     ans[j]=tmp[j];
     89         }
     90     }
     91 }
     92 
     93 inline void print()
     94 {
     95     printf("Case #%d: ",cas);
     96     for(int i=1;i<=anslen;i++)
     97         printf("%c",ans[i]);
     98     puts("");
     99 }
    100 
    101 int main()
    102 {
    103     for(int i=0;i<=9;i++)
    104         c[i]=i+'0';
    105     for(int i=10;i<=15;i++)
    106         c[i]=i-10+'a';
    107     mi[1]=8;mi[2]=4;mi[3]=2;mi[4]=1;
    108     int t;
    109     scanf("%d",&t);
    110     for(cas=1;cas<=t;cas++)
    111     {
    112         prework();
    113         mainwork();
    114         print();
    115     }
    116     return 0;
    117 }
    View Code

    C Palindrome Mouse

    题解:给一个串,问这个串里所有本质不同的回文子串,有多少对满足一个串是另一个的子串。

    首先是next边,很显然,一条next链上,除奇根偶根,所有父亲都是儿子的子串。
    其次是fail边,又又又很显然,一条fail链上,父亲是儿子的后缀,所以除奇根偶根所有父亲都是儿子的子串

    对于每个节点,答案就是其next链上除根外的父亲个数+fail链上除根外的父亲个数。

    于是还要想办法去个重。在dfs并且对每个节点跳fail树统计的时候,打个vis标记(当前节点也要标记,next链和fail链重的时候就可能会跳到这里),如果下次跳的时候发现了vis,就可以停止了,这样就简单的保证了不交叉,并且防止了fail树重复跳带来的复杂度。

    参考代码:

    #include <bits/stdc++.h>
    using namespace std;
    typedef long long ll;
    const int maxn=1e5+5;
    int T;
    char s[maxn];
    ll ans;
    
    struct PAM{
        int nxt[maxn][26];
        int fail[maxn];
        int len[maxn];
        int S[maxn];
        int dp[maxn];
        bool vis[maxn];
        int last,n,p;
        
        int NewNode(int l) 
        {
            memset(nxt[p],0,sizeof(nxt[p]));
            len[p]=l;
            dp[p]=0;
            return p++;
        }
    
        void Init() 
        {
            ans=0;
            n=last=p=0;
            NewNode(0);
            NewNode(-1);
            S[n]=-1;
            fail[0]=1;
        }
    
        int GetFail(int x) 
        {
            while(S[n-len[x]-1]!=S[n]) x=fail[x];
            return x;
        }
    
        void add(int c) 
        {
            S[++n]=c;
            int cur=GetFail(last);
            if(!nxt[cur][c]) 
            {
                int now=NewNode(len[cur]+2);
                fail[now]=nxt[GetFail(fail[cur])][c];
                nxt[cur][c]=now;
            }
            last=nxt[cur][c];
        }
    
        void dfs(int x,int fa) 
        {
            int cnt=0,cx=x; vis[x]=1;
            while(fail[cx]!=0&&fail[cx]!=1&&!vis[fail[cx]]) 
                cx=fail[cx],vis[cx]=1,++cnt;
            dp[x]=cnt;
            if(x!=1&&x!=0&&fa!=0&&fa!=1) 
                dp[x]=dp[fa]+cnt+1;
            ans+=dp[x];
            for(int i=0;i<26;++i){if(nxt[x][i]) dfs(nxt[x][i],x);}
            vis[x]=0; cx=x;
            while(cnt--) cx=fail[cx],vis[cx]=0;
        }
    
        void work()
        {
            Init();
            for(int i=1,len=strlen(s+1);i<=len;i++) add(s[i]-'a');
            dfs(1,1);
            dfs(0,0);
        }
    
    } pam;
    
    
    int main() 
    {
        scanf("%d", &T);
        for(int cas=1;cas<=T;++cas) 
        {
            scanf("%s",s+1);
            pam.work();
            printf("Case #%d: %lld
    ",cas,ans);
        }
        return 0;
    }
    View Code

    D Move

    题解:https://blog.csdn.net/liufengwei1/article/details/98352448

     1 #include<bits/stdc++.h>
     2 using namespace std;
     3 int v[1005];int n,k;
     4 struct p{
     5     int x;
     6     p(){}
     7     p(int x):x(x){}
     8     friend bool operator<(p a,p b)
     9     {
    10         return a.x>b.x;
    11     }
    12 }pp[1005];
    13 set<p> s;
    14 set<p> :: iterator it;
    15 int num[1006];
    16 bool check(int vol)
    17 {
    18     int tol=k,d;
    19     s.clear();
    20     for(int i=1;i<=n;i++)
    21     {   
    22         if(num[pp[i].x]==0)
    23             s.insert(pp[i]);
    24         num[pp[i].x]++;
    25     }
    26     while(tol&& ((int)s.size())>0)
    27     {
    28         tol--;
    29         p res(vol);
    30         it=s.lower_bound(res);
    31         while(it!=s.end())
    32         {
    33             d=(*it).x;
    34             res.x-=d;
    35             num[d]--;
    36             if(num[d]==0)
    37                 s.erase(it);
    38             it=s.lower_bound(res);
    39         }
    40     }
    41     for(int i=1;i<=n;i++)
    42         num[pp[i].x]=0;
    43     if(s.size()>0) return false;
    44     return true;
    45 }
    46 int main()
    47 {
    48     int t;
    49     scanf("%d",&t);
    50      
    51     for(int kace=1;kace<=t;kace++)
    52     {
    53         scanf("%d%d",&n,&k);
    54         int r=0;
    55         for(int i=1;i<=n;i++) scanf("%d",&v[i]),r+=v[i];
    56         for(int i=1;i<=n;i++) pp[i].x=v[i];
    57         int l=0,mid;
    58         int ans=r;
    59         bool flag;
    60         while(l+1<r)
    61         {
    62             mid=(l+r)>>1;
    63             flag=false;
    64             for(int j=max(l+1,mid-25);j<=mid;j++)
    65             if(check(j))
    66                 flag=true;
    67             if(flag)
    68                 r=mid;
    69             else
    70                 l=mid;
    71         }
    72         for(int j=max(1,r-100);j<=r;j++)
    73         if(check(j))
    74         {
    75             ans=j;
    76             break;
    77         }
    78         printf("Case #%d: %d
    ",kace,ans);
    79     }
    80 }  
    View Code

    E Androgynos

    题解:https://blog.csdn.net/liufengwei1/article/details/98388543

      1 #include<bits/stdc++.h>
      2 using namespace std;
      3 int f[2005];
      4 int g[2005][2005];
      5 int main()
      6 {
      7     int t;
      8     scanf("%d",&t);
      9     for(int kace=1;kace<=t;kace++)
     10     {
     11         int n;scanf("%d",&n);
     12         int ty=n%4;int id;
     13         if(ty==2||ty==3)
     14         {
     15             printf("Case #%d: No
    ",kace);
     16             continue;
     17         }
     18         for(int i=1;i<=n;i++)
     19             for(int j=1;j<=n;j++)
     20                 g[i][j]=0;
     21         if(ty==1)
     22         {
     23             for(int i=ty;i<=n-4;i+=4)
     24             {
     25                 for(int j=1;j<=i;j++)
     26                 {
     27                     g[i+2][j]=1;
     28                     g[j][i+2]=1;
     29                     g[i+3][j]=1;
     30                     g[j][i+3]=1;
     31                 }
     32                 g[i+1][i+2]=g[i+2][i+1]=1;
     33                 g[i+2][i+3]=g[i+3][i+2]=1;
     34                 g[i+3][i+4]=g[i+4][i+3]=1;
     35             }
     36             printf("Case #%d: Yes
    ",kace);
     37             for(int i=1;i<=n;i++)
     38             {
     39                 for(int j=1;j<=n;j++)
     40                 {
     41                     printf("%d",g[i][j]);
     42                 }
     43                 puts("");
     44             }
     45             for(int i=1;i<=n;i++)
     46                 f[i]=i;
     47             for(int i=1;i<=n/4;i++)
     48             {
     49                 id=(i-1)*4+1;
     50                 swap(f[id+2],f[id+3]);
     51                 swap(f[id+1],f[id+2]);
     52                 swap(f[id+3],f[id+4]);
     53             }
     54             for(int i=1;i<=n;i++)
     55                 printf("%d%c",f[i],(i==n)?'
    ':' ');
     56             /*bool flag=true;
     57             for(int i=1;i<=n;i++)
     58                 for(int j=1;j<=n;j++)
     59                 if(i!=j)
     60                 if(g[f[i]][f[j]]!=(g[i][j]^1))
     61                     flag=false;
     62             if(flag)
     63                 puts("Yes");*/
     64             //变换顺序
     65         }
     66         else
     67         {
     68             ty=4;
     69             g[1][2]=g[2][1]=g[2][3]=g[3][2]=g[3][4]=g[4][3]=1;
     70             for(int i=ty;i<=n-4;i+=4)
     71             {
     72                 for(int j=1;j<=i;j++)
     73                 {
     74                     g[i+2][j]=1;
     75                     g[j][i+2]=1;
     76                     g[i+3][j]=1;
     77                     g[j][i+3]=1;
     78                 }
     79                 g[i+1][i+2]=g[i+2][i+1]=1;
     80                 g[i+2][i+3]=g[i+3][i+2]=1;
     81                 g[i+3][i+4]=g[i+4][i+3]=1;
     82             }
     83             printf("Case #%d: Yes
    ",kace);
     84             for(int i=1;i<=n;i++)
     85             {
     86                 for(int j=1;j<=n;j++)
     87                 {
     88                     printf("%d",g[i][j]);
     89                 }
     90                 puts("");
     91             }
     92             for(int i=1;i<=n;i++)
     93                 f[i]=i;
     94             for(int i=1;i<=n/4;i++)
     95             {
     96                 id=(i-1)*4;
     97                 swap(f[id+2],f[id+3]);
     98                 swap(f[id+1],f[id+2]);
     99                 swap(f[id+3],f[id+4]);
    100             }
    101             for(int i=1;i<=n;i++)
    102                 printf("%d%c",f[i],(i==n)?'
    ':' ');
    103             /*bool flag=true;
    104             for(int i=1;i<=n;i++)
    105                 for(int j=1;j<=n;j++)
    106                 if(i!=j)
    107                 if(g[f[i]][f[j]]!=(g[i][j]^1))
    108                     flag=false;
    109             if(flag)
    110                 puts("Yes");*/
    111         }
    112     }
    113 }
    View Code

    F K-ary Heap

    unsolved

    G Is Today Friday?

    unsolved

    H Train Driver

    unsolved

    I Can They Go to Galar?

    unsolved

    J Upgrading Technology

    单调队列维护一下,但是枚举获得d1--dj的时候要注意一定要保证有一个技能只严格升级到了j

     1 #include<bits/stdc++.h>
     2 #define maxl 1010
     3 using namespace std;
     4 
     5 int n,m,cas;
     6 long long ans=0;
     7 int c[maxl][maxl];
     8 long long q[maxl][maxl];
     9 int qtop[maxl],qhead[maxl];
    10 long long sum[maxl][maxl];
    11 long long d[maxl];
    12 
    13 inline void prework()
    14 {
    15     scanf("%d%d",&n,&m);
    16     for(int i=1;i<=n;i++)
    17         for(int j=1;j<=m;j++)
    18         {
    19             scanf("%lld",&sum[i][j]);
    20             sum[i][j]=-sum[i][j];
    21         }
    22     for(int i=1;i<=m;i++)
    23         scanf("%lld",&d[i]);
    24     for(int i=1;i<=n;i++)
    25         qtop[i]=0,qhead[i]=1;
    26     for(int i=1;i<=n;i++)
    27         for(int j=0;j<=m;j++)
    28         {
    29             if(j>0)
    30                 sum[i][j]+=sum[i][j-1];
    31             while(qtop[i]>0 && sum[i][j]>=sum[i][q[i][qtop[i]]])
    32                 qtop[i]--;
    33             q[i][++qtop[i]]=j;    
    34         }
    35 }
    36 
    37 inline void mainwork()
    38 {
    39     long long sumd=0,sumt;ans=0;
    40     for(int j=0;j<=m;j++)
    41     {
    42         sumd+=d[j];sumt=0;
    43         for(int i=1;i<=n;i++)
    44         {
    45             while(q[i][qhead[i]]<j)
    46                 qhead[i]++;
    47             sumt+=sum[i][q[i][qhead[i]]];    
    48         }
    49         ans=max(sumd+sumt,ans);
    50     }
    51 }
    52 
    53 inline void print()
    54 {
    55     printf("Case #%d: %lld
    ",cas,ans);
    56 }
    57 
    58 int main()
    59 {
    60     int t;
    61     scanf("%d",&t);
    62     for(cas=1;cas<=t;cas++)
    63     {
    64         prework();
    65         mainwork();
    66         print();
    67     }
    68     return 0;
    69 }
    View Code
  • 相关阅读:
    AC自动机模板
    hdu 6034 贪心模拟 好坑
    UVA 10870
    hdu 2604 递推 矩阵快速幂
    hdu 3117 Fibonacci Numbers 矩阵快速幂+公式
    hdu 1575 Tr A 矩阵快速幂
    POJ_1151 扫描线+离散化+线段树
    HDU_2227 求不减子序列的个数(树状数组+DP)
    深夜敲模板_5——KMP
    深夜敲模板_4——无向图的割顶和桥
  • 原文地址:https://www.cnblogs.com/csushl/p/11301496.html
Copyright © 2020-2023  润新知