2012金华邀请赛

 

 

模拟赛链接

A 第一个水题

要知道units digit的意思  (个位数) 

有一点点小繁琐。

  1 #include <iostream>

  2 #include<cstdio>

  3 #include<cstring>

  4 #include<algorithm>

  5 #include<stdlib.h>

  6 #include<cmath>

  7 using namespace std;

  8 #define N 35

  9 int a[N],b[N];

 10 int o1[N],o2[N];

 11 struct node

 12 {

 13     int di;

 14     int v;

 15 }p[N];

 16 int judge(int x,int y,int n)

 17 {

 18     int i;

 19     for(i = 0 ;i < n ; i++)

 20     {

 21         int g = 0;

 22         while(x+g<=y&&o2[i+g]==o1[x+g])

 23         g++;

 24 //        if(x==1&&y==2)

 25 //        printf("%d, %d %d %d\n ",i,g,o2[i],o1[x]);

 26         if(x+g>y)

 27         return 1;

 28     }

 29     return 0;

 30 }

 31 bool cmp(node a,node b)

 32 {

 33     if(a.di==b.di)

 34     return a.v<b.v;

 35     return a.di<b.di;

 36 }

 37 bool ccmp(int a,int b)

 38 {

 39     return a>b;

 40 }

 41 int main()

 42 {

 43     int t,i,j,n1,n2;

 44     cin>>t;

 45     while(t--)

 46     {

 47         scanf("%d%d",&n1,&n2);

 48         for(i = 0;i < n1 ;i++)

 49         scanf("%d",&a[i]);

 50         for(i = 0 ;i< n2 ; i++)

 51         scanf("%d",&b[i]);

 52         sort(a,a+n1,ccmp); sort(b,b+n2,ccmp);

 53         int g1=1,g2=1,g;

 54         o1[0] = a[0];

 55         for(i = 1; i < n1 ; i++)

 56         if(a[i]!=a[i-1])

 57         {

 58             o1[g1++] = a[i];

 59         }

 60         o2[0] = b[0];

 61         for(i = 1;i < n2 ; i++)

 62         if(b[i]!=b[i-1])

 63         {

 64             o2[g2++] = b[i];

 65         }

 66         int st=-1,en=-1,mz=-1,maxz=-1;

 67         for(i = 0; i < g1 ; i++)

 68         {

 69             for(j = i ; j < g1 ; j++)

 70             {

 71                 if(judge(i,j,g2))

 72                 {

 73 //                    cout<<i<<" "<<j<<endl;

 74                     int mm = -1;

 75                     for(int e = i ; e <= j; e++)

 76                     mm = max(mm,o1[e]);

 77                     if(maxz<=j-i+1)

 78                     {

 79                         if(maxz<j-i+1||mm>mz)

 80                         {

 81                             st = i;

 82                             en = j;

 83                             mz = mm;

 84                             maxz = j-i+1;

 85                         }

 86                     }

 87                 }

 88             }

 89         }

 90         if(st==-1)

 91         {

 92             puts("NONE");

 93             continue;

 94         }

 95         g = 0;

 96         for(i = st ; i<= en; i++)

 97         {

 98             p[g].v = o1[i];

 99             p[g].di = o1[i]%10;

100             g++;

101         }

102         for(i = 0 ;i < g-1 ; i++)

103         printf("%d ",p[i].v);

104         printf("%d\n",p[i].v);

105         sort(p,p+g,cmp);

106         for(i = 0 ;i < g-1 ; i++)

107         printf("%d ",p[i].v);

108         printf("%d\n",p[i].v);

109     }

110     return 0;

111 }
View Code

 

队友过的,待填。。

C

卡时限的奇葩题。

预处理出以k点为最高价格点时到其它点的单源最短路径,在询问时用这个n种情况依次更新u,v;

minz = min(minz,w[k][u]+w[k][v]+p[k]);

直接写可能会超时,反正我超了N久,需要把询问先读进来,再依次更新。

  1 #include <iostream>

  2 #include<cstdio>

  3 #include<cstring>

  4 #include<algorithm>

  5 #include<stdlib.h>

  6 #include<vector>

  7 #include<cmath>

  8 #include<queue>

  9 #include<set>

 10 using namespace std;

 11 #define N 1010

 12 #define M 20010

 13 #define LL long long

 14 #define INF 1e18

 15 const double eps = 1e-8;

 16 const double pi = acos(-1.0);

 17 const double inf = ~0u>>2;

 18 vector<int>ed[N][2];

 19 int cot[N],co[N][N];

 20 LL w[N][N],dis[N],mm[M];

 21 bool vis[N];

 22 struct node

 23 {

 24     int c,id;

 25 }p[N];

 26 struct nodd

 27 {

 28     int u,v;

 29 }qi[M];

 30 struct mode

 31 {

 32     int u;

 33     LL w;

 34     friend bool operator <(const mode &a,const mode &b)

 35     {

 36         return a.w>b.w;

 37     }

 38 };

 39 void spfa(int st,int n)

 40 {

 41     memset(vis,0,sizeof(vis));

 42     queue<mode>q;

 43     int i;

 44     mode tt,ts;

 45     for(i = 1; i <= n; i++)

 46     {

 47         dis[i] = INF;

 48     }

 49     ts.u = st;

 50     ts.w = 0;

 51     q.push(ts);

 52     vis[st] = 1;

 53     dis[st] = 0;

 54     while(!q.empty())

 55     {

 56         tt = q.front();

 57         int u = tt.u;

 58         q.pop();

 59         vis[u] = 0;

 60         for(i = 0 ;i  < ed[u][0].size(); i++)

 61         {

 62             int v = ed[u][0][i];

 63             int w = ed[u][1][i];

 64             if(p[v].c>p[st].c) continue;

 65             if(dis[v]>dis[u]+w)

 66             {

 67                 dis[v] = dis[u]+w;

 68                 if(!vis[v])

 69                 {

 70                     ts.u = v;

 71                     ts.w = dis[v];

 72                     vis[v] = 1;

 73                     q.push(ts);

 74                 }

 75             }

 76         }

 77     }

 78 }

 79 bool cmp(node a,node b)

 80 {

 81     return a.c>b.c;

 82 }

 83 int main()

 84 {

 85     int n,m,i,j;

 86     while(scanf("%d%d",&n,&m)&&n&&m)

 87     {

 88         for(i = 1; i <= n ; i++)

 89         {

 90             scanf("%d",&p[i].c);

 91             p[i].id = i;

 92             ed[i][0].clear();

 93             ed[i][1].clear();

 94         }

 95         for(i = 1; i <= m; i++)

 96         {

 97             int u,v,w;

 98             scanf("%d%d%d",&u,&v,&w);

 99             ed[u][0].push_back(v);

100             ed[u][1].push_back(w);

101             ed[v][0].push_back(u);

102             ed[v][1].push_back(w);

103         }

104         ;

105         int q;

106         scanf("%d",&q);

107         for(i = 1; i <= q ; i++)

108         {

109             scanf("%d%d",&qi[i].u,&qi[i].v);

110             mm[i] = INF;

111         }

112         for(i = 1 ;i <= n ; i++)

113         {

114             spfa(i,n);

115             for(j = 1; j <= q ; j++)

116             {

117                 mm[j] = min(mm[j],dis[qi[j].u]+dis[qi[j].v]+p[i].c);

118             }

119         }

120         for(i  = 1; i < q; i++)

121         {

122             if(mm[i]==INF)

123             printf("-1\n");

124             else

125             printf("%lld\n",mm[i]);

126         }

127         if(mm[q]==INF)

128         puts("-1");

129         else

130         printf("%lld\n",mm[q]);

131         puts("");

132     }

133     return 0;

134 }
View Code

 

D

线段树水题,有段时间没写,居然lz忘记更新,卡了几个小时。。。

  1 #include <iostream>

  2 #include<cstdio>

  3 #include<cstring>

  4 #include<algorithm>

  5 #include<stdlib.h>

  6 #include<cmath>

  7 using namespace std;

  8 #define N 200010

  9 #define INF 0xfffffff

 10 int a[N],b[N],lz[N<<2];

 11 int s[N<<2];

 12 void up(int w)

 13 {

 14     s[w] = max(s[w<<1],s[w<<1|1]);

 15 }

 16 void build(int l,int r,int w)

 17 {

 18     lz[w] = 0;

 19     if(l==r)

 20     {

 21         s[w] = a[l];

 22         return ;

 23     }

 24     int m = (l+r)>>1;

 25     build(l,m,w<<1);

 26     build(m+1,r,w<<1|1);

 27     up(w);

 28 }

 29 void down(int w,int m)

 30 {

 31     if(lz[w]!=0)

 32     {

 33         s[w<<1]+=lz[w];

 34         s[w<<1|1]+=lz[w];

 35         lz[w<<1]+=lz[w];

 36         lz[w<<1|1]+=lz[w];

 37         lz[w] = 0;

 38     }

 39 }

 40 void update(int x,int y,int d,int l,int r,int w)

 41 {

 42     if(x<=l&&y>=r)

 43     {

 44         s[w] += d;

 45         lz[w] += d;

 46         return ;

 47     }

 48     down(w,r-l+1);

 49     int m = (l+r)>>1;

 50     if(x<=m)

 51     update(x,y,d,l,m,w<<1);

 52     if(y>m)

 53     update(x,y,d,m+1,r,w<<1|1);

 54     up(w);

 55 }

 56 int query(int x,int y,int l,int r,int w)

 57 {

 58     if(x<=l&&y>=r)

 59     return s[w];

 60     int m  =(l+r)>>1;

 61     down(w,r-l+1);

 62     int res = -INF;

 63     if(x<=m)

 64     res = max(query(x,y,l,m,w<<1),res);

 65     if(y>m)

 66     res = max(query(x,y,m+1,r,w<<1|1),res);

 67     return res;

 68 }

 69 int main()

 70 {

 71     int i,n,t,m,k;

 72     scanf("%d",&t);

 73     while(t--)

 74     {

 75         scanf("%d%d%d",&n,&m,&k);

 76         for(i = 1 ;i <= n; i++)

 77             scanf("%d",&b[i]);

 78         a[n+1] = 0;

 79         int g = n;

 80         for(i = n ; i >= 1 ; i--)

 81         {

 82             a[i] = a[i+1]+b[i];

 83             if(n-i+1>k)

 84             {

 85                 a[i]-=b[g--];

 86             }

 87         }

 88         n = n-k+1;

 89         build(1,n,1);

 90         while(m--)

 91         {

 92             int x,y,z;

 93             scanf("%d%d%d",&z,&x,&y);

 94             if(z==0)

 95             {

 96                 update(max(x-k+1,1),min(x,n),y-b[x],1,n,1);

 97                 b[x] = y;

 98             }

 99             else if(z==1)

100             {

101                 update(max(x-k+1,1),min(x,n),b[y]-b[x],1,n,1);

102                 update(max(y-k+1,1),min(y,n),b[x]-b[y],1,n,1);

103                 swap(b[x],b[y]);

104             }

105             else

106             printf("%d\n",query(x,y-k+1,1,n,1));

107         }

108     }

109     return 0;

110 }
View Code

 

E

简单几何题,枚举所在点到所有线段端点的直线,可以想到最多穿墙的线肯定是过端点的。

注意一点,给出的线段会有与你枚举的直线重合的线段

  1 #include <iostream>

  2 #include <algorithm>

  3 #include <cmath>

  4 #include <cstring>

  5 #include <string>

  6 #include <cstdio>

  7 using namespace std;

  8 #define eps 1e-8

  9 #define zero(x) (((x)>0?(x):-(x)) < eps)

 10 struct point

 11 {

 12     double x,y;

 13 }p[4001];

 14 struct line

 15 {

 16     point a,b;

 17 };

 18 double dis(point p1,point p2)

 19 {

 20     return (p1.x-p2.x)*(p1.x-p2.x) + (p1.y-p2.y)*(p1.y-p2.y);

 21 }

 22 double xmult(point p1,point p2,point p0)

 23 {

 24     return (p1.x-p0.x)*(p2.y-p0.y) - (p2.x-p0.x)*(p1.y-p0.y);

 25 }

 26 int pinline(point p,line l)

 27 {

 28     return zero(xmult(p,l.a,l.b))&&(l.a.x-p.x)*(l.b.x-p.x) < eps&&(l.a.y-p.y)*(l.b.y-p.y) < eps;

 29 }

 30 point inter(point u1,point u2,point v1,point v2)

 31 {

 32     point ret = u1;

 33     double t = ((u1.x-v1.x)*(v1.y-v2.y)-(u1.y-v1.y)*(v1.x-v2.x))

 34                 /((u1.x-u2.x)*(v1.y-v2.y)-(u1.y-u2.y)*(v1.x-v2.x));

 35     ret.x += (u2.x-u1.x)*t;

 36     ret.y += (u2.y-u1.y)*t;

 37     return ret;

 38 }

 39 int pingxing(line u,line v)

 40 {

 41     return zero((u.a.x-u.b.x)*(v.a.y-v.b.y)-(v.a.x-v.b.x)*(u.a.y-u.b.y));

 42 }

 43 int nopoint(point p,line l)

 44 {

 45     return pinline(p,l)&&(!zero(p.x-l.a.x)||!zero(p.y-l.a.y))&&(!zero(p.x-l.b.x)||!zero(p.y-l.b.y));

 46 }

 47 int main()

 48 {

 49     int n,t,i,j,ans,num;

 50     scanf("%d",&t);

 51     while(t--)

 52     {

 53         scanf("%d",&n);

 54         for(i = 1;i <= 2*n;i ++)

 55         {

 56             scanf("%lf%lf",&p[i].x,&p[i].y);

 57         }

 58         ans = 0;

 59         scanf("%lf%lf",&p[0].x,&p[0].y);

 60         for(i = 1;i <= 2*n;i ++)

 61         {

 62             num = 0;

 63             for(j = 1;j <= n;j ++)

 64             {

 65                 line u,v,ti;

 66                 point temp;

 67                 u.a = p[0];

 68                 u.b = p[i];

 69                 v.a = p[2*j-1];

 70                 v.b = p[2*j];

 71                 ti.a = p[0];

 72                 ti.b = p[i];

 73                 if(pinline(p[2*j],ti))

 74                 {

 75                     num++;

 76                     continue;

 77                 }

 78                 ti.b = p[2*j];

 79                 if(pinline(p[i],ti))

 80                 {

 81                     num++;

 82                     continue;

 83                 }

 84                 if(pingxing(u,v)) continue;

 85                 temp = inter(p[0],p[i],p[2*j-1],p[2*j]);

 86                 if(pinline(temp,v))

 87                 {

 88                     line tt;

 89                     tt.a = p[0];

 90                     tt.b = temp;

 91                     if(pinline(p[i],tt))

 92                     num ++;

 93                     else

 94                     {

 95                         tt.a = p[0];

 96                         tt.b = p[i];

 97                         if(pinline(temp,tt))

 98                         num++;

 99                     }

100                 }

101             }

102             ans = max(ans,num);

103         }

104         printf("%d\n",ans);

105     }

106     return 0;

107 }
View Code

 

H

ac自动机,比赛的时候没来得及看,看了也不一定会。。

这个题不管 去除子串这个条件就是裸自动机,可以先进行裸自动机把需要的串标记出来,再在已经标记的串里面进行自动机的查找去掉它所含有的子串。

因为数据挺大,可以省掉strlen()这个操作,全改为指针操作。

模板里面有句话错了,wa了N久。。

  1 #include <iostream>

  2 #include<cstdio>

  3 #include<cstring>

  4 #include<algorithm>

  5 #include<stdlib.h>

  6 #include<vector>

  7 #include<cmath>

  8 #include<queue>

  9 #include<set>

 10 using namespace std;

 11 #define N 3100010

 12 #define M 1100

 13 #define NN 5100000

 14 #define LL long long

 15 #define INF 0xfffffff

 16 const double eps = 1e-8;

 17 const double pi = acos(-1.0);

 18 const double inf = ~0u>>2;

 19 const int child_num = 26;

 20 bool o[2510];

 21 char s[NN],sr[NN],vir[M];

 22 char dig[20],ss[2510][M];

 23 class ACAutomo

 24 {

 25 private:

 26     int ch[N][child_num];

 27     int val[N];

 28     int fail[N];

 29     int Q[N];

 30     int id[128];

 31     int sz;

 32 public:

 33     void init()

 34     {

 35         fail[0] = 0;

 36         for(int i = 'A'; i <= 'Z' ; i++)

 37             id[i] = i-'A';

 38     }

 39     void reset()

 40     {

 41         memset(ch[0],0,sizeof(ch[0]));

 42         memset(o,0,sizeof(o));

 43         sz = 1;

 44     }

 45     void insert(char *a,int key)

 46     {

 47         int p = 0 ;

 48         for( ; *a !='\0'; a++)

 49         {

 50             int d = id[*a];

 51             if(ch[p][d]==0)

 52             {

 53                 memset(ch[sz],0,sizeof(ch[sz]));

 54                 val[sz] = 0;

 55                 ch[p][d] = sz++;

 56             }

 57             p = ch[p][d];

 58         }

 59         val[p]=key;

 60     }

 61     void construct()

 62     {

 63         int i,head=0,tail = 0;

 64         for(i = 0 ; i < child_num ; i++)

 65         {

 66             if(ch[0][i])

 67             {

 68                 Q[tail++] = ch[0][i];

 69                 fail[ch[0][i]] = 0;

 70             }

 71         }

 72         while(head!=tail)

 73         {

 74             int u = Q[head++];

 75             for(i = 0; i < child_num ; i++)

 76             {

 77                 if(ch[u][i])

 78                 {

 79                     Q[tail++] = ch[u][i];

 80                     fail[ch[u][i]] = ch[fail[u]][i];

 81                 }

 82                 else

 83                     ch[u][i] = ch[fail[u]][i];

 84             }

 85         }

 86     }

 87     void work(char *s)

 88     {

 89         int p = 0;

 90         for( ; *s!='\0' ; s++)

 91         {

 92             int d = id[*s];

 93             p = ch[p][d];

 94             int tmp = p;

 95             if(val[tmp])

 96             {

 97                 o[val[tmp]] = 1;

 98                 continue;

 99             }

100             while(tmp!=0&&val[tmp]!=0)

101             {

102                 o[val[tmp]] = 1;

103                 tmp = fail[tmp];

104             }

105         }

106     }

107     void solve(char *s)

108     {

109         int p = 0;

110         for( ; *s!='\0' ; s++)

111         {

112             int d = id[*s];

113             p = ch[p][d];

114             int tmp = p;

115             while(tmp!=0&&val[tmp]!=0)

116             {

117                 o[val[tmp]] = 0;

118                 tmp = fail[tmp];

119             }

120         }

121     }

122 } ac;

123 void change(char *sr,int k)

124 {

125     int g=0;

126     for( ; *sr!='\0' ; sr++)

127     {

128         if((*sr)>='A'&&(*sr)<='Z')

129         {

130             if(k!=-1)

131                 ss[k][g++] = (*sr);

132             else

133                 s[g++] = (*sr);

134         }

135         else if((*sr)=='[')

136         {

137             sr++;

138             int e = 0;

139             while((*sr)>='0'&&(*sr)<='9')

140             {

141                 dig[e++] = (*sr);

142                 sr++;

143             }

144             dig[e] = '\0';

145             int num = atoi(dig);

146             while(num--)

147             {

148                 if(k!=-1)

149                     ss[k][g++] = (*sr);

150                 else

151                     s[g++] = (*sr);

152             }

153             sr++;

154         }

155     }

156     if(k!=-1)

157         ss[k][g] = '\0';

158     else

159         s[g] = '\0';

160 }

161 int main()

162 {

163     int n,i;

164     ac.init();

165     int t;

166     scanf("%d",&t);

167     int tt = 0;

168     while(t--)

169     {

170         tt++;

171         scanf("%d",&n);

172         ac.reset();

173         for(i = 1; i <= n; i++)

174         {

175             scanf("%s",vir);

176             change(vir,i);

177             ac.insert(ss[i],i);

178         }

179         //cout<<n<<endl;

180         ac.construct();

181         scanf("%s",sr);

182 //        if(tt>12)

183 //        {

184 //            puts("1");

185 //            continue;

186 //        }

187         change(sr,-1);

188         ac.work(s);

189         for(i = 1 ; i <= n ; i++)

190         {

191             if(o[i])

192             {

193                 ac.solve(ss[i]);

194                 o[i] = 1;

195             }

196         }

197         int num = 0;

198         for(i = 1; i <= n; i++)

199             if(o[i]) num++;

200         printf("%d\n",num);

201     }

202     return 0;

203 }
View Code

 

 

 

你可能感兴趣的:(2012)