A. Mishka and Game
题解:
水题。。比较大小即可
代码:
#include<bits/stdc++.h> using namespace std; #define pb push_back #define mp make_pair #define se second #define fs first #define ll long long #define CLR(x) memset(x,0,sizeof x) #define SZ(x) ((int)(x).size()) #define FOR(it,c) for(__typeof((c).begin()) it=(c).begin();it!=(c).end();it++) typedef pair<int,int> P; const double eps=1e-9; const int maxn=100100; ll read() { ll x=0,f=1;char ch=getchar(); while(ch<‘0‘||ch>‘9‘){if(ch==‘-‘)f=-1;ch=getchar();} while(ch>=‘0‘&&ch<=‘9‘){x=x*10+ch-‘0‘;ch=getchar();} return x*f; } //----------------------------------------------------------------------------- int main() { int n,a,b,m,c; m=c=0; cin>>n; for(int i=1;i<=n;i++) { cin>>a>>b; if(a>b) m++; if(a<b) c++; } if(m==c) cout<<"Friendship is magic!^^"<<endl; if(m>c) cout<<"Mishka"<<endl; if(m<c) cout<<"Chris"<<endl; }
B. Mishka and trip
题解:
也是水题,,预处理一下前缀和。。使用map记录已用的城市即可
代码:
#include<bits/stdc++.h> using namespace std; #define pb push_back #define mp make_pair #define se second #define fs first #define ll long long #define CLR(x) memset(x,0,sizeof x) #define SZ(x) ((int)(x).size()) #define FOR(it,c) for(__typeof((c).begin()) it=(c).begin();it!=(c).end();it++) typedef pair<int,int> P; const double eps=1e-9; const int maxn=100100; ll read() { ll x=0,f=1;char ch=getchar(); while(ch<‘0‘||ch>‘9‘){if(ch==‘-‘)f=-1;ch=getchar();} while(ch>=‘0‘&&ch<=‘9‘){x=x*10+ch-‘0‘;ch=getchar();} return x*f; } //----------------------------------------------------------------------------- int c[maxn],id[maxn]; set<int> s; int main() { int n,k; cin>>n>>k; ll sum=0,cnt=0,sum1=0; for(int i=1;i<=n;i++) { cin>>c[i]; sum+=c[i]; } for(int i=1;i<=k;i++) { cin>>id[i]; s.insert(id[i]); } for(int i=1;i<=k;i++) { cnt+=(sum-c[id[i]])*c[id[i]]; if(i==1) { sum1+=c[id[i]]; continue; } cnt-=sum1*c[id[i]]; sum1+=c[id[i]]; } for(int i=2;i<=n;i++) { if(s.count(i)||s.count(i-1)) continue; cnt+=c[i]*c[i-1]; } if(!s.count(1)&&!s.count(n)) cnt+=c[1]*c[n]; cout<<cnt<<endl; return 0; }
C. Chris and Road
题解:
给你一个多边形,以速度v驶过y轴,然后一个人从原点开始,以速度不超过u,在y轴到达(0,w),问在不与多边形相撞的情况下,最短花费时间..
一看是几何体。。。瞬间就不想做了。。因为计算几何基础为0,后来看题解的发现就是一个贪心过程
如果每个点在人到达相应的位置之前度过或之后,那么直接w/u;
否则就max((w-y)/u+ x/v),贪心是玄学。。。。
二分也可以做。
二分的话,也是分2种情况
对于所有点,要么在之前全部超过了。直接w/u;
要么,在全部之后,时间为w/u+t;
二分t,使得 对于每个店.x/v<y/u+t..
转化一下变为 x*u-y*v-t*v*u<0;
使得这满足的最小t
代码:
贪心
#include<bits/stdc++.h> using namespace std; #define pb push_back #define mp make_pair #define se second #define fs first #define ll long long #define CLR(x) memset(x,0,sizeof x) #define SZ(x) ((int)(x).size()) #define FOR(it,c) for(__typeof((c).begin()) it=(c).begin();it!=(c).end();it++) #define lson l,m,rt<<1 #define rson m+1,r,rt<<1|1 #define MAXF 2097152 typedef pair<int,int> P; const double eps=1e-9; const int maxn=1e5+10; ll read() { ll x=0,f=1;char ch=getchar(); while(ch<‘0‘||ch>‘9‘){if(ch==‘-‘)f=-1;ch=getchar();} while(ch>=‘0‘&&ch<=‘9‘){x=x*10+ch-‘0‘;ch=getchar();} return x*f; } //----------------------------------------------------------------------------- int main() { int n,early=1,late=1; double w,v,u,x,y,t=0; cin>>n>>w>>v>>u; for(int i=1;i<=n;i++) { cin>>x>>y; if(y/u>x/v) late=0; if(y/u<x/v) early=0; t=max(t,x/v+(w-y)/u); } if(early||late) t=w/u; cout<<setprecision(10)<<t<<endl; return 0; }
二分(抄的quailty的代码ORZ)
#include<bits/stdc++.h> using namespace std; #define pb push_back #define mp make_pair #define se second #define fs first #define ll long long #define CLR(x) memset(x,0,sizeof x) #define SZ(x) ((int)(x).size()) #define FOR(it,c) for(__typeof((c).begin()) it=(c).begin();it!=(c).end();it++) #define lson l,m,rt<<1 #define rson m+1,r,rt<<1|1 #define MAXF 2097152 typedef pair<int,int> P; const double eps=1e-9; const int maxn=1e5+10; ll read() { ll x=0,f=1;char ch=getchar(); while(ch<‘0‘||ch>‘9‘){if(ch==‘-‘)f=-1;ch=getchar();} while(ch>=‘0‘&&ch<=‘9‘){x=x*10+ch-‘0‘;ch=getchar();} return x*f; } //----------------------------------------------------------------------------- pair<double,double> p[maxn]; int sgn(double x) { if(x>eps) return 1; if(x<-eps) return -1; return 0; } bool Check(double u,double v,double t,int n,int ty) { for(int i=1;i<=n;i++) if(ty*sgn(u*p[i].fs-v*p[i].se-u*v*t)<0) return false; return true; } int main() { int n; double w,v,u; cin>>n>>w>>v>>u; for(int i=1;i<=n;i++) cin>>p[i].fs>>p[i].se; if(Check(u,v,0,n,1)) cout<<setprecision(10)<<w/u<<endl; else { double l=0,r=2e9; for(int i=0;i<100;i++) { double m=(l+r)/2; if(Check(u,v,m,n,-1)) r=m; else l=m; } cout<<setprecision(10)<<w/u+(l+r)/2<<endl; } return 0; }
D. Mishka and Interesting sum
题解:
求m个询问l,r,求区间[l,r]出现的偶数次的数的异或和
根据异或和的性质[l,r]直接异或求的是出现奇数次的数的异或和
那么,考虑如何将奇数次的数的异或和变成偶数,偶数变成奇数?。。。。将全部数是次数出现减一即可
离线+树状数组即可
代码:
#include<bits/stdc++.h> using namespace std; #define pb push_back #define mp make_pair #define se second #define fs first #define ll long long #define CLR(x) memset(x,0,sizeof x) #define SZ(x) ((int)(x).size()) #define FOR(it,c) for(__typeof((c).begin()) it=(c).begin();it!=(c).end();it++) #define lson l,m,rt<<1 #define rson m+1,r,rt<<1|1 #define INF 2097152 typedef pair<int,int> P; const double eps=1e-9; const int maxn=1000100; ll read() { ll x=0,f=1;char ch=getchar(); while(ch<‘0‘||ch>‘9‘){if(ch==‘-‘)f=-1;ch=getchar();} while(ch>=‘0‘&&ch<=‘9‘){x=x*10+ch-‘0‘;ch=getchar();} return x*f; } //----------------------------------------------------------------------------- int a[maxn],c[INF]; P p[maxn],s[maxn]; map<int,int> pre; map<P,int> ans; void add(int x,int d) { while(x>0) { c[x]^=d; x-=(x&-x); } } int sum(int x) { int cnt=0; while(x<INF) { cnt^=c[x]; x+=(x&-x); } return cnt; } bool cmp(P a,P b) { if(a.se==b.se) return a.fs<b.fs; return a.se<b.se; } int main() { int n,m; n=read(); for(int i=1;i<=n;i++) a[i]=read(); m=read(); for(int i=1;i<=m;i++) { p[i].fs=read();p[i].se=read(); s[i]=p[i]; } sort(p+1,p+m+1,cmp); int r=1; for(int i=1;i<=m;i++) { while(r<=p[i].se) { add(pre[a[r]],a[r]); pre[a[r]]=r; r++; } ans[p[i]]=sum(p[i].fs); } for(int i=1;i<=m;i++) printf("%d\n",ans[s[i]]); return 0; }
时间: 2024-10-08 22:24:35