A1 100pts
暴力kmp
#include<bits/stdc++.h> #define R register int using namespace std; namespace Luitaryi { const int N=100010; char s[N*3],s1[N],s2[N]; int l,l1,l2,nxt1[N],nxt2[N]; vector <int> p1,p2; inline void main() { scanf("%s",s+1); R p=1,q,tmpl=strlen(s+1); while(s[p]!=',') ++p; q=p+1; while(s[q]!=',') ++q; memcpy(s1+1,s+p+1,sizeof(char)*(q-p-1)); memcpy(s2+1,s+q+1,sizeof(char)*(tmpl-q)); l1=q-p-1,l2=tmpl-q,l=p-1; for(R i=2,j=0;i<=l1;i++) { while(j&&s1[i]!=s1[j+1]) j=nxt1[j]; if(s1[j+1]==s1[i]) ++j; nxt1[i]=j; } for(R i=2,j=0;i<=l2;i++) { while(j&&s2[i]!=s2[j+1]) j=nxt2[j]; if(s2[j+1]==s2[i]) ++j; nxt2[i]=j; } for(R i=1,j=0;i<=l;i++) { while(j&&s[i]!=s1[j+1]) j=nxt1[j]; if(s[i]==s1[j+1]) ++j; if(j==l1) p1.push_back(i),j=nxt1[j]; } for(R i=1,j=0;i<=l;i++) { while(j&&s[i]!=s2[j+1]) j=nxt2[j]; if(s[i]==s2[j+1]) ++j; if(j==l2) p2.push_back(i-l2+1),j=nxt2[j]; } if(!p1.size()||!p2.size()) puts("-1"); else if(p1[0]>=p2[p2.size()-1]) puts("-1"); else printf("%d\n",p2[p2.size()-1]-p1[0]-1); } } signed main() {Luitaryi::main(); return 0;}
A2 没卡精度+写挂 10pts
考试时直接用 set<pair<long double,long double> > 判重(也是没谁了)
当时特别想切掉这道题,于是想了各种情况(就是以为精度不会挂)
然后获得了10pts的好成绩。
后来问了问大家
woc为什么想这么少都能90pts(原来大家都在卡精度)
下午听说有人改对了听了听他的思路
哈哈我能hack你(我xx考试时还能白想那么多?)
瞬间hack掉std。
原因是都没有把在圆上的点扔掉。
下面是改了的std
#include <cstdio> #include <cstring> #include <algorithm> #include <cmath> using namespace std; typedef double db; const int N = 1000, oo = (int)2e9; const db eps = 1e-7; struct vec { db x, y; }cs[N + 10]; vec operator + (const vec &a, const vec &b) { return (vec){a.x + b.x, a.y + b.y}; } vec operator - (const vec &a, const vec &b) { return (vec){a.x - b.x, a.y - b.y}; } vec operator * (const db &a, const vec &b) { return (vec){a * b.x, a * b.y}; } db operator * (const vec &a, const vec &b) { return a.x * b.y - a.y * b.x; } bool Eq(const db &a, const db &b) { return fabs(a - b) < eps; } bool cmp(const vec &a, const vec &b) { return a.x < b.x || (Eq(a.x, b.x) && a.y < b.y); } bool operator != (const vec &a, const vec &b) { return !Eq(a.x, b.x) || !Eq(a.y, b.y); } db Dist(const vec &a) { return sqrt(a.x * a.x + a.y * a.y); } struct line { vec p, t; }a[N + 10]; int n, m, r, cnt; int l1, r1, l2, r2; vec Cross(line a, line b) { vec dt = b.p - a.p; if (Eq(a.t * b.t, 0)) return (vec){oo, oo}; db t = (dt * b.t) / (a.t * b.t); return a.p + (t * a.t); } int main() { scanf("%d\n%d\n", &r, &n); int ans = 1; for (int i = 1; i <= n; ++i) { scanf("%d%d%d%d\n", &l1, &r1, &l2, &r2); a[i].p = (vec){(db)l1, (db)r1}, a[i].t = (vec){(db)(l2 - l1), (db)(r2 - r1)}, cnt = 0; for (int j = 1; j < i; ++j) { vec c = Cross(a[j], a[i]); if (c.x == oo) continue; db ds = Dist(c); if (ds > r || Eq(ds, r)) continue; cs[++cnt] = c; } sort(cs + 1, cs + cnt + 1, cmp); int tot = 0; cs[cnt + 1].x = oo; for (int i = 1; i <= cnt; ++i) if (cs[i] != cs[i + 1]) ++tot; ans += tot + 1; } printf("%d\n", ans); return 0; }
(说了这么多就是把小于等于换成小于)
A3 第一次贪心贪对 85pts
好像做过类似的。。。就瞎xx贪。。
然后就MLE了(1e+6空限64MB)
后来在linux上改过了
#include<bits/stdc++.h> #define R register int using namespace std; namespace Luitaryi { inline int g() { R x=0,f=1; register char ch; while(!isdigit(ch=getchar())) f=ch=='-'?-1:f; do x=x*10+(ch^48); while(isdigit(ch=getchar())); return x*f; } const int Inf=0x3f3f3f3f,N=1000010; int n,k,ans,cnt,vr[N<<1],nxt[N<<1],fir[N],mx[N],mn[N]; inline void add(int u,int v) { vr[++cnt]=v,nxt[cnt]=fir[u],fir[u]=cnt; vr[++cnt]=u,nxt[cnt]=fir[v],fir[v]=cnt; } inline void dfs(int u,int fa) { mn[u]=Inf,mx[u]=0; for(R i=fir[u];i;i=nxt[i]) { if(vr[i]==fa) continue; dfs(vr[i],u); mx[u]=max(mx[u],mn[vr[i]]+mx[vr[i]]<=k?0:mx[vr[i]]+1); mn[u]=min(mn[u],mn[vr[i]]+1); } if(mn[u]+mx[u]<=k) mx[u]=0; if(mx[u]>=k) ++ans,mn[u]=0,mx[u]=0; } inline void main() { n=g(),k=g(); for(R i=1,u,v;i<n;++i) u=g(),v=g(),add(u,v); dfs(1,0); if(mx[1]+mn[1]>k) ++ans; printf("%d\n",ans); } } signed main() {Luitaryi::main(); return 0;}
B1
二分。
#include<bits/stdc++.h> #define R register int using namespace std; namespace Luitaryi { inline int g() { R x=0,f=1; register char ch; while(!isdigit(ch=getchar())) f=ch=='-'?-1:f; do x=x*10+(ch^48); while(isdigit(ch=getchar())); return x*f; } const int N=100010; int n,m,x[N],y[N]; inline void main() { n=g(); for(R i=1;i<=n;++i) x[i]=g(); for(R i=1;i<=n;++i) y[i]=g(); sort(x+1,x+n+1),sort(y+1,y+n+1); m=g(); while(m--) { R X=g(),Y=g(),l=0,r=n; while(l<r) { R md=l+r+1>>1; if(1ll*Y*x[md]+1ll*X*y[md]>=1ll*x[md]*y[md]) l=md; else r=md-1; } printf("%d\n",l); } } } signed main() {Luitaryi::main(); return 0;}
B2
倍增,维护链上最小值。
#include<bits/stdc++.h> #define R register int using namespace std; namespace Luitaryi { inline int g() { R x=0,f=1; register char ch; while(!isdigit(ch=getchar())) f=ch=='-'?-1:f; do x=x*10+(ch^48); while(isdigit(ch=getchar())); return x*f; } const int N=100010,L=17,Inf=1e9; int n,m,cnt; int vr[N<<1],nxt[N<<1],fir[N],fa[N][L],mn[N][L],f[N]; struct node {int k,w; node() {} node(int _k,int _w) {k=_k,w=_w;}}; vector <node> mem[N]; inline void add(int u,int v) { vr[++cnt]=v,nxt[cnt]=fir[u],fir[u]=cnt; vr[++cnt]=u,nxt[cnt]=fir[v],fir[v]=cnt; } inline void dfs(int u) { f[u]=Inf; for(R t=1;t<L;++t) fa[u][t]=fa[fa[u][t-1]][t-1], mn[u][t]=min(mn[u][t-1],mn[fa[u][t-1]][t-1]); if(u!=1) for(R i=0,lim=mem[u].size();i<lim;++i) { R k=mem[u][i].k,tmp=u,crt=Inf; for(R t=L-1;~t;--t) if(k>=(1<<t)) crt=min(crt,mn[tmp][t]),tmp=fa[tmp][t],k-=(1<<t); f[u]=min(f[u],crt+mem[u][i].w); } if(u==1) f[u]=0; for(R i=fir[u];i;i=nxt[i]) { R v=vr[i]; if(fa[v][0]) continue; fa[v][0]=u,mn[v][0]=f[u],dfs(v); } } inline void main() { n=g(),m=g(); for(R i=1,u,v;i<n;++i) u=g(),v=g(),add(u,v); for(R i=1,u,k,w;i<=m;++i) u=g(),k=g(),w=g(),mem[u].push_back(node(k,w)); dfs(1); m=g(); for(R i=1,u;i<=m;++i) u=g(),printf("%d\n",f[u]); } } signed main() {Luitaryi::main(); return 0;}
B3
模拟?
咕?
总结
不要写挂,稳稳稳。
注意精度,之前没有发现double这么。。。