zoukankan      html  css  js  c++  java
  • loli的测试-2018.12.9

    模拟赛-2018.12.9

      这是NOIP之后第一次模拟赛...但是考的比较悲惨。

      非常喜欢写考试总结,不知道为什么...

      T1:https://www.luogu.org/problemnew/show/P4147

      暴力加剪枝,跑的非常快。正解是悬线法,应该会更快一些。

      
     1 # include <cstdio>
     2 # include <iostream>
     3 # include <cstring>
     4 # include <algorithm>
     5 # define R register int
     6 
     7 using namespace std;
     8 
     9 const int maxn=1003;
    10 int n,m,ans;
    11 int a[maxn][maxn],u[maxn][maxn];
    12 char c[5];
    13 
    14 int main()
    15 {
    16     scanf("%d%d",&n,&m);
    17     for (R i=1;i<=n;++i)
    18         for (R j=1;j<=m;++j)
    19         {
    20             scanf("%s",c+1);
    21             if(c[1]=='R') a[i][j]=0;
    22             else a[i][j]=1;    
    23             if(a[i][j])
    24                 u[i][j]=u[i-1][j]+1; 
    25         }
    26     for (R i=1;i<=n;++i)
    27         for (R j=1;j<=m;++j)
    28         {
    29             int s=u[i][j];
    30             for (R k=j;k>=1;--k)
    31             {
    32                 s=min(s,u[i][k]);
    33                 if(s==0) break;
    34                 if(s*j<=ans) break;
    35                 ans=max(ans,(j-k+1)*s);
    36             }
    37         }
    38     printf("%d",ans*3);
    39     return 0;
    40 }
    T1

      T2:https://www.lydsy.com/JudgeOnline/problem.php?id=2351

      矩阵哈希,但是被卡常了,其实本机跑的还挺快的,但是一用Cena测就变慢很多,不知道为什么。后来将所有的哈希值存下来排序,再利用单调性离线做就过了。

      因为不想写双哈希,所以想了一种比较奇妙的哈希方法,只要出题人没想到可以这样做就不会被卡了。首先对于每一行进行哈希,然后再对哈希值进行哈希,这里的精髓是变换角度的时候换一个base,几乎不可能被卡。

      
     1 # include <cstdio>
     2 # include <iostream>
     3 # include <cstring>
     4 # include <algorithm>
     5 # define R register int
     6 # define ULL int
     7 
     8 using namespace std;
     9 
    10 const int maxn=1002;
    11 const int base1=233;
    12 const int base2=97;
    13 int q,m,n,at,a,b,f[maxn][maxn],st,cnt;
    14 ULL hash1[maxn][maxn],hash2[maxn][maxn],po1[maxn],po2[maxn],Hash[101],s[maxn*maxn];
    15 char c[maxn];
    16 struct ask
    17 {
    18     int id,ans;
    19     ULL v;
    20 }A[maxn];
    21 ULL get_hash (int i,int l,int r) { return hash1[i][r]-hash1[i][l]*po1[r-l]; }
    22 bool cmp (ask a,ask b) { return a.v<b.v; }
    23 bool cmp1 (ask a,ask b) { return a.id<b.id; }
    24 
    25 int main()
    26 {
    27     scanf("%d%d%d%d",&m,&n,&a,&b);
    28     po1[0]=1;
    29     for (R i=1;i<=n;++i)
    30         po1[i]=po1[i-1]*base1;
    31     po2[0]=1;
    32     for (R i=1;i<=n;++i)
    33         po2[i]=po2[i-1]*base2;
    34     for (R i=1;i<=m;++i)
    35     {
    36         scanf("%s",c+1);
    37         for (R j=1;j<=n;++j)
    38         {
    39             if(c[j]=='0') f[i][j]=2;
    40             else f[i][j]=3; 
    41             hash1[i][j]=hash1[i][j-1]*base1+f[i][j];
    42         }
    43     }
    44     for (R i=1;i<=m;++i)
    45         for (R j=b;j<=n;++j)
    46             hash2[i][j]=hash2[i-1][j]*base2+get_hash(i,j-b,j);
    47     for (R i=a;i<=m;++i)
    48         for (R j=b;j<=n;++j)
    49             s[++st]=hash2[i][j]-hash2[i-a][j]*po2[a];
    50     sort(s+1,s+1+st);
    51     scanf("%d",&q);
    52     while(q--)
    53     {
    54         memset(Hash,0,sizeof(Hash));
    55         for (R i=1;i<=a;++i)
    56         {
    57             scanf("%s",c+1);
    58             for (R j=1;j<=b;++j)
    59                 if(c[j]=='0') f[i][j]=2;
    60                 else f[i][j]=3;
    61         }
    62         for (R i=1;i<=a;++i)
    63             for (R j=1;j<=b;++j)
    64                 Hash[i]=Hash[i]*base1+f[i][j];
    65         for (R i=1;i<=a;++i)
    66             Hash[i]=Hash[i-1]*base2+Hash[i];
    67         A[++at].id=++cnt;
    68         A[at].v=Hash[a];
    69     }
    70     int p=1;
    71     sort(A+1,A+1+at,cmp);
    72     for (R i=1;i<=at;++i)
    73     {
    74         while(p<=st&&s[p]<A[i].v) p++;
    75         if(s[p]==A[i].v) A[i].ans=1;
    76     }
    77     sort(A+1,A+1+at,cmp1);
    78     for (R i=1;i<=at;++i)
    79         printf("%d
    ",A[i].ans);
    80     return 0;
    81 }
    T2

      T3:https://www.lydsy.com/JudgeOnline/problem.php?id=1398

      题意概述:最小表示法板子题;

      ...可惜我不会.考场上手推了一个不知道复杂度多少的算法,但是跑的非常快,只是读错了输出要求丢了十分,下次要认真读题.

      说一下我自己编的做法:

      首先将字符串复制一份拼在后面:abac->abacabac.

      从之前的半段找到最小的字母作为开头,会发现有两个:

      

      那么把这两个点都加入队列里面,下一轮接着比较,发现第一个更优,此时当前最优解只有一个了,就是最终答案.

      但是这样做对于随机数据的确很快,对于构造的数据就变得很慢了,举个例子:aaaaa;

      但是这个算法并没有就此而至,要巧妙的应用最优解的性质,比如说这样,当前两个解都扫描到了相同的长度,但还没有分出高下.

      

      显然后面那个"可能的最优解"没有必要再保留了,因为绿色段最好也就是和蓝色段一样好(否则它就是最优解了),所以前者将来可能制造的最优解不会比后者劣,加上这个优化后跑的飞快,也许均摊证一下复杂度会变得非常科学?如果有人会证明或者Hack请私信我,谢谢~

      
     1 # include <cstdio>
     2 # include <iostream>
     3 # include <cstring>
     4 # include <algorithm>
     5 # define R register int
     6 
     7 using namespace std;
     8 
     9 const int maxn=2000006;
    10 char s[maxn],t[maxn],ds[maxn];
    11 int len,f,vis[maxn];
    12 int q1[maxn],q2[maxn];
    13 
    14 void min_dic ()
    15 {
    16     memset(vis,0,sizeof(vis));
    17     int minn=1000,beg=1;
    18     int t1=0,t2=0;
    19     for (R i=1;i<=len;++i)
    20         minn=min(minn,(int)s[i]);
    21     for (R i=1;i<=len;++i)
    22         ds[i]=ds[i+len]=s[i];
    23     for (R i=1;i<=len;++i)
    24         if(ds[i]==minn) q1[++t1]=i;
    25     for (R i=1;i<len;++i)
    26     {
    27         t2=0;
    28         for (R j=1;j<=t1;++j)
    29             if(q1[j]!=0&&vis[ q1[j] ]==0) q2[++t2]=q1[j];            
    30         if(t2==1)
    31         {
    32             beg=q2[1];
    33             break;
    34         }
    35         t1=0;
    36         minn=1000;
    37         for (R j=1;j<=t2;++j)
    38             minn=min(minn,(int)ds[ q2[j]+i ]);
    39         for (R j=1;j<=t2;++j)
    40             if(ds[ q2[j]+i ]==minn) vis[ q2[j]+i ]=true;
    41             else q2[j]=0;
    42         t1=t2;
    43         for (R j=1;j<=t1;++j)
    44             q1[j]=q2[j];
    45     }
    46     for (R i=1;i<=len;++i)
    47         s[i]=ds[i-1+beg];
    48 }
    49 
    50 int main()
    51 {
    52     scanf("%s",s+1);
    53     len=strlen(s+1);
    54     min_dic();
    55     for (R i=1;i<=len;++i)
    56         t[i]=s[i];
    57     memset(s,0,sizeof(s));
    58     scanf("%s",s+1);
    59     min_dic();
    60     int f=0;
    61     for (R i=1;i<=len;++i)
    62         if(t[i]!=s[i]) f=1;
    63     if(f) printf("No
    ");
    64     else printf("Yes
    "),printf("%s",s+1);
    65     return 0;
    66 }
    T3

      T4:https://www.luogu.org/problemnew/show/P2860

      题意概述:边双板子题;

      一个小结论:缩完边双后的新图如果有$n$个叶子,那么需要再加$f(n)$条边才能变成一个大边双.

      $$f(n)=egin {Bmatrix}0,n=1\ frac{n+1}{2},othersend{Bmatrix}$$

      
     1 # include <cstdio>
     2 # include <iostream>
     3 # include <cstring>
     4 # include <algorithm>
     5 # define R register int
     6 
     7 using namespace std;
     8 
     9 const int maxn=5002;
    10 const int maxm=20004;
    11 int k,n,m,h=1,firs[maxn],x,y,sta[maxn],Tp,ans,id[maxn],low[maxn],cnt,d[maxn],bp,color[maxn];
    12 struct edge
    13 {
    14     int too,nex;
    15 }g[maxm];
    16 
    17 void add (int x,int y)
    18 {
    19     g[++h].nex=firs[x];
    20     g[h].too=y;
    21     firs[x]=h;
    22 }
    23 
    24 void dfs (int x,int las)
    25 {
    26     id[x]=low[x]=++cnt;
    27     sta[++Tp]=x;
    28     int j;
    29     for (R i=firs[x];i;i=g[i].nex)
    30     {
    31         if(i==(las^1)) continue;
    32         j=g[i].too;
    33         if(!id[j]) dfs(j,i);
    34         low[x]=min(low[x],low[j]);
    35     }
    36     if(id[x]==low[x])
    37     {
    38         color[x]=++bp;
    39         while(sta[Tp]!=x)
    40         {
    41             color[ sta[Tp] ]=bp;
    42             Tp--;
    43         }
    44         Tp--;
    45     }
    46 }
    47 
    48 int main()
    49 {
    50     scanf("%d%d",&n,&m);
    51     for (R i=1;i<=m;++i)
    52     {
    53         scanf("%d%d",&x,&y);
    54         add(x,y);
    55         add(y,x);
    56     }
    57     for (R i=1;i<=n;++i)
    58         if(!id[i]) dfs(i,-1);
    59     for (R i=1;i<=n;++i)
    60         for (R j=firs[i];j;j=g[j].nex)
    61         {
    62             k=g[j].too;
    63             if(color[i]!=color[k]) d[ color[k] ]++,d[ color[i] ]++;
    64         }
    65     for (R i=1;i<=bp;++i)
    66         if(d[i]==2) ans++;
    67     if(ans==1) printf("0");
    68     else printf("%d",(ans+1)/2);
    69     return 0;
    70 }
    T4

      T5:https://www.luogu.org/problemnew/show/P4819

      题意概述:有$n$个人,$m$对认识关系(单向),其中有一个人是杀手,如果问普通人,那他就会告诉你他认识的人中有没有杀手,否则就会被杀,每个人是杀手的概率相同,求最优策略下不被杀的概率.

      显然要先缩点,然后入度为零的问一问,就没了...吗?

      考试时这么写,挂成了25分.这道题还需要用到一点人类智慧.

      举个例子:5 0这组数据,被杀的概率用我的做法做是1,但其实是0.8,因为如果问了四个人都不是杀手,第五个人就不用问了,推广一下,如果有一个入度为0的联通分量的大小为一,且连出去的边指向的点入度不为一,这个点就是一个可有可无的点,不过即使有很多这样的点也只能删一个,注意一下.

      
      1 # include <cstdio>
      2 # include <iostream>
      3 # include <cstring>
      4 # include <vector>
      5 # include <algorithm>
      6 # define R register int
      7 
      8 using namespace std;
      9 
     10 const int maxn=100005;
     11 const int maxm=300005;
     12 int k,ans,h,x,y,n,m,siz[maxn],firs[maxn],id[maxn],low[maxn],color[maxn],bp,cnt,r[maxn],sta[maxn],Tp,vis[maxn];
     13 struct edge
     14 {
     15     int too,nex;
     16 }g[maxm];
     17 struct edg
     18 {
     19     int x,y;
     20 }ed[maxm];
     21 vector <int> v[maxn];
     22 
     23 void add (int x,int y)
     24 {
     25     g[++h].too=y;
     26     g[h].nex=firs[x];
     27     firs[x]=h;
     28 }
     29 
     30 void dfs (int x)
     31 {
     32     id[x]=low[x]=++cnt;
     33     vis[x]=true;
     34     sta[++Tp]=x;
     35     int j;
     36     for (R i=firs[x];i;i=g[i].nex)
     37     {
     38         j=g[i].too;
     39         if(!id[j])
     40         {
     41             dfs(j);
     42             low[x]=min(low[x],low[j]);
     43         }
     44         else
     45         {
     46             if(vis[j]) low[x]=min(low[x],low[j]);
     47         }
     48     }
     49     if(id[x]==low[x])
     50     {
     51         color[x]=++bp;
     52         vis[x]=false;
     53         siz[bp]++;
     54         while(sta[Tp]!=x)
     55         {
     56             color[ sta[Tp] ]=bp;
     57             vis[ sta[Tp] ]=false;
     58             Tp--;
     59             siz[bp]++;
     60         }
     61         Tp--;
     62     }
     63 }
     64 
     65 bool check (int x)
     66 {
     67     if(siz[x]>1) return false;
     68     int sz=v[x].size();
     69     for (R i=0;i<sz;++i)
     70         if(r[ v[x][i] ]==1) return false;
     71     return true;
     72 }
     73 
     74 bool cmp (edg a,edg b)
     75 {
     76     if(a.x==b.x) return a.y<b.y;
     77     return a.x<b.x;
     78 }
     79 
     80 int main()
     81 {
     82     scanf("%d%d",&n,&m);
     83     for (R i=1;i<=m;++i)
     84         scanf("%d%d",&ed[i].x,&ed[i].y);
     85     sort(ed+1,ed+1+m,cmp);
     86     for (R i=1;i<=m;++i)
     87         if(ed[i].x!=ed[i-1].x||ed[i].y!=ed[i-1].y) add(ed[i].x,ed[i].y);
     88     for (R i=1;i<=n;++i)
     89         if(!id[i]) dfs(i);
     90     for (R i=1;i<=n;++i)
     91         for (R j=firs[i];j;j=g[j].nex)
     92         {
     93             k=g[j].too;
     94             if(color[i]!=color[k]) r[ color[k] ]++,v[ color[i] ].push_back(color[k]);
     95         }
     96     for (R i=1;i<=bp;++i)
     97         if(r[i]==0) ans++;
     98     for (R i=1;i<=bp;++i)
     99         if((r[i]==0)&&check(i))
    100         {
    101             ans--;
    102             break;
    103         }
    104     ans=n-ans;
    105     printf("%.6lf",(double)ans/n);
    106     return 0;
    107 }
    T5

      今天又是被烜神仙吊着锤的一天呢,自闭了,还是要提高知识水平呀.

    ---shzr

  • 相关阅读:
    OGG初始化之使用Oracle Data Pump加载数据
    OGG初始化之使用数据库实用程序加载数据
    OGG初始加载过程概述
    管理凭证存储中的身份
    使用ENCKEYS方法加密数据
    使用主密钥和钱包方法加密数据
    配置Oracle GoldenGate安全性
    建立Oracle GoldenGate凭证
    System.DllNotFoundException:“无法加载 DLL“SQLite.Interop.dll”: 找不到指定的模块 的解决方法
    记录一下Oracle添加、查看表、字段注释及导出ddl
  • 原文地址:https://www.cnblogs.com/shzr/p/10093267.html
Copyright © 2011-2022 走看看