2020 CCPC Wannafly Winter Camp Day5 Div.1&2
大失败。
- A 签到题,题面太长没做。
- B 树上传递闭包问题。原本是想着倒着做能求解答案,使用并查集,后来发现并查集并不对 正解是维护一个可到达点的数量利用树的特点容斥了一下。
code
//#include<bits/stdc++.h>
#include<iostream>
#include<cstdio>
#include<ctime>
#include<cctype>
#include<queue>
#include<deque>
#include<stack>
#include<iostream>
#include<iomanip>
#include<cstdio>
#include<cstring>
#include<string>
#include<ctime>
#include<cmath>
#include<cctype>
#include<cstdlib>
#include<queue>
#include<deque>
#include<stack>
#include<vector>
#include<algorithm>
#include<utility>
#include<bitset>
#include<set>
#include<map>
#define ll long long
#define db double
#define INF 1000000000000000000ll
#define inf 1000000001
#define ldb long double
#define pb push_back
#define put_(x) printf("%d ",x);
#define get(x) x=read()
#define gt(x) scanf("%d",&x)
#define gi(x) scanf("%lf",&x)
#define put(x) printf("%d\n",x)
#define putl(x) printf("%lld\n",x)
#define rep(p,n,i) for(int i=p;i<=n;++i)
#define go(x) for(int i=lin[x],tn=ver[i];i;tn=ver[i=nex[i]])
#define pii pair<int,int>
#define mk make_pair
#define P 1000000007ll
#define gf(x) scanf("%lf",&x)
#define pf(x) ((x)*(x))
#define uint unsigned long long
#define ui unsigned
#define EPS 1e-10
#define sq sqrt
#define S second
#define F first
#define mod 998244353
#define r(x) c[x].r
#define l(x) c[x].l
#define cc(x) c[x].cc
#define mx2(x) t[x].mx2
#define max(x,y) ((x)<(y)?y:x)
using namespace std;
char *fs,*ft,buf[1<<15];
inline char gc()
{
return (fs==ft&&(ft=(fs=buf)+fread(buf,1,1<<15,stdin),fs==ft))?0:*fs++;
}
inline int read()
{
int x=0,f=1;char ch=gc();
while(ch<'0'||ch>'9'){if(ch=='-')f=-1;ch=gc();}
while(ch>='0'&&ch<='9'){x=x*10+ch-'0';ch=gc();}
return x*f;
}
const int MAXN=500010;
int n,m;
int a[MAXN],b[MAXN];
int f[MAXN],c[MAXN],w[MAXN];
int main()
{
//freopen("1.in","r",stdin);
n=read();m=read();
rep(1,n-1,i)
{
f[i]=1;
a[i]=read(),b[i]=read();
}
f[n]=1;
rep(1,m,j)w[j]=read();
for(int i=m;i>=1;--i)
{
int x=a[w[i]],y=b[w[i]];
f[x]=f[y]=f[x]+f[y]-c[w[i]];
c[w[i]]=f[x];
}
rep(1,n,i)printf("%d ",f[i]);
return 0;
}
- C 一个简单的区间dp 利用归纳法来求不同区间的代价,不同区间我使用树状数组来数点。
code
//#include<bits/stdc++.h>
#include<iostream>
#include<cstdio>
#include<ctime>
#include<cctype>
#include<queue>
#include<deque>
#include<stack>
#include<iostream>
#include<iomanip>
#include<cstdio>
#include<cstring>
#include<string>
#include<ctime>
#include<cmath>
#include<cctype>
#include<cstdlib>
#include<queue>
#include<deque>
#include<stack>
#include<vector>
#include<algorithm>
#include<utility>
#include<bitset>
#include<set>
#include<map>
#define ll long long
#define db double
#define INF 1000000000000000000ll
#define inf 1000000001
#define ldb long double
#define pb push_back
#define put_(x) printf("%d ",x);
#define get(x) x=read()
#define gt(x) scanf("%d",&x)
#define gi(x) scanf("%lf",&x)
#define put(x) printf("%d\n",x)
#define putl(x) printf("%lld\n",x)
#define rep(p,n,i) for(int i=p;i<=n;++i)
#define go(x) for(int i=lin[x],tn=ver[i];i;tn=ver[i=nex[i]])
#define pii pair<int,int>
#define mk make_pair
#define P 1000000007ll
#define gf(x) scanf("%lf",&x)
#define pf(x) ((x)*(x))
#define uint unsigned long long
#define ui unsigned
#define EPS 1e-10
#define sq sqrt
#define S second
#define F first
#define mod 998244353
#define v(x) t[x].v
#define r(x) t[x].r
#define l(x) t[x].l
#define mx2(x) t[x].mx2
#define max(x,y) ((x)<(y)?y:x)
using namespace std;
char *fs,*ft,buf[1<<15];
inline char gc()
{
return (fs==ft&&(ft=(fs=buf)+fread(buf,1,1<<15,stdin),fs==ft))?0:*fs++;
}
inline int read()
{
int x=0,f=1;char ch=gc();
while(ch<'0'||ch>'9'){if(ch=='-')f=-1;ch=gc();}
while(ch>='0'&&ch<='9'){x=x*10+ch-'0';ch=gc();}
return x*f;
}
const int MAXN=510,N=200010;
int n,m;
int f[MAXN][MAXN];//f[i][j]表示i~j这个区间所形成的线段树的最小值。
//f[i][j]=min{f[i][k]+f[k+1][j]+cost[i][j]};
int cost[MAXN][MAXN];
struct wy
{
int l,r;
}t[N],h[N];
inline int cmp(wy a,wy b){return a.l<b.l;}
inline int cmp1(wy a,wy b){return a.r<b.r;}
int c[MAXN],v[MAXN],s[MAXN],b[MAXN][MAXN];
inline void add(int x,int y)
{
while(x<=n)
{
c[x]+=y;
x+=x&(-x);
}
}
inline int ask(int x)
{
int cnt=0;
while(x)
{
cnt+=c[x];
x-=x&(-x);
}
return cnt;
}
inline void add1(int x,int y)
{
while(x<=n)
{
s[x]+=y;
x+=x&(-x);
}
}
inline int ask1(int x)
{
int cnt=0;
while(x)
{
cnt+=s[x];
x-=x&(-x);
}
return cnt;
}
int main()
{
//freopen("1.in","r",stdin);
n=read();m=read();
rep(1,m,i){l(i)=read();r(i)=read();add(r(i),1),++b[l(i)][r(i)];h[i]=t[i];}
sort(t+1,t+1+m,cmp);
sort(h+1,h+1+m,cmp1);
//rep(1,m,i)cout<<t[i].l<<' '<<t[i].r<<endl;
int w=m;
for(int i=n;i>=1;--i)
{
v[i]=m-w;
while(l(w)==i)--w;
}
w=0;int wc=1,ws=0;
rep(1,n,i)
{
while(l(ws+1)==i)add1(r(ws+1),1),++ws;
rep(i,n,j)
{
int ww=w+v[j];//无用
int w1=ask(j)-b[i][j];//包含
int w3=ws-ask1(j-1);//被包含
int w2=m-ww-w1-w3;//相交
cost[i][j]=w2+w1;
if(i==j)cost[i][j]+=w3;
else cost[i][j]-=w3;
f[i][j]=inf;
}
while(h[w+1].r==i)++w;
while(l(wc)==i)add(r(wc),-1),++wc;
f[i][i]=cost[i][i];
}
/*rep(1,n,i)
{
rep(i,n,j)
cout<<i<<' '<<j<<' '<<cost[i][j]<<endl;
cout<<endl;
}*/
rep(2,n,len)
{
for(int i=1;i<=n-len+1;++i)
{
int j=i+len-1;
rep(i,j-1,k)
{
f[i][j]=min(f[i][j],f[i][k]+f[k+1][j]+cost[i][j]);
}
}
}
printf("%d\n",f[1][n]);
return 0;
}
- D 一个求解多个圆相交部分的计算几何,没太看懂相交的面积怎么算 咕咕。
- E 一个简单的枚举问题。
code
//#include<bits/stdc++.h>
#include<iostream>
#include<cstdio>
#include<ctime>
#include<cctype>
#include<queue>
#include<deque>
#include<stack>
#include<iostream>
#include<iomanip>
#include<cstdio>
#include<cstring>
#include<string>
#include<ctime>
#include<cmath>
#include<cctype>
#include<cstdlib>
#include<queue>
#include<deque>
#include<stack>
#include<vector>
#include<algorithm>
#include<utility>
#include<bitset>
#include<set>
#include<map>
#define ll long long
#define db double
#define INF 1000000000000000000ll
#define inf 1000000001
#define ldb long double
#define pb push_back
#define put_(x) printf("%d ",x);
#define get(x) x=read()
#define gt(x) scanf("%d",&x)
#define gi(x) scanf("%lf",&x)
#define put(x) printf("%d\n",x)
#define putl(x) printf("%lld\n",x)
#define rep(p,n,i) for(int i=p;i<=n;++i)
#define go(x) for(int i=lin[x],tn=ver[i];i;tn=ver[i=nex[i]])
#define pii pair<int,int>
#define mk make_pair
#define P 1000000007ll
#define gf(x) scanf("%lf",&x)
#define pf(x) ((x)*(x))
#define uint unsigned long long
#define ui unsigned
#define EPS 1e-10
#define sq sqrt
#define S second
#define F first
#define mod 998244353
#define r(x) c[x].r
#define l(x) c[x].l
#define cc(x) c[x].cc
#define mx2(x) t[x].mx2
#define max(x,y) ((x)<(y)?y:x)
using namespace std;
char *fs,*ft,buf[1<<15];
inline char gc()
{
return (fs==ft&&(ft=(fs=buf)+fread(buf,1,1<<15,stdin),fs==ft))?0:*fs++;
}
inline int read()
{
int x=0,f=1;char ch=gc();
while(ch<'0'||ch>'9'){if(ch=='-')f=-1;ch=gc();}
while(ch>='0'&&ch<='9'){x=x*10+ch-'0';ch=gc();}
return x*f;
}
const int MAXN=310;
int n;
int a[MAXN],b[MAXN];
int c[MAXN][MAXN];
int main()
{
//freopen("1.in","r",stdin);
n=read();
rep(1,n,i)a[i]=read();
rep(1,4,i)b[i]=read();
for(int i=n;i>=1;--i)
{
rep(1,n,j)c[i][j]=c[i+1][j];
++c[i][a[i]];
}
ll ans=0;
rep(1,n,i)
{
rep(i+1,n,j)
{
if(b[1]==b[2]&&a[i]!=a[j])continue;
if(a[i]==a[j]&&b[1]!=b[2])continue;
rep(j+1,n,k)
{
if(b[1]==b[3]&&a[i]!=a[k])continue;
if(b[1]!=b[3]&&a[i]==a[k])continue;
if(b[2]==b[3]&&a[j]!=a[k])continue;
if(b[2]!=b[3]&&a[j]==a[k])continue;
if(b[1]==b[4]){ans+=c[k+1][a[i]];continue;}
if(b[2]==b[4]){ans+=c[k+1][a[j]];continue;}
if(b[3]==b[4]){ans+=c[k+1][a[k]];continue;}
int ww=c[k+1][a[i]];
if(b[1]!=b[2])ww+=c[k+1][a[j]];
if(b[1]!=b[3]&&b[2]!=b[3])ww+=c[k+1][a[k]];
ans+=n-k-ww;
}
}
}
printf("%lld\n",ans);
return 0;
}
code
//#include<bits/stdc++.h>
#include<iostream>
#include<cstdio>
#include<ctime>
#include<cctype>
#include<queue>
#include<deque>
#include<stack>
#include<iostream>
#include<iomanip>
#include<cstdio>
#include<cstring>
#include<string>
#include<ctime>
#include<cmath>
#include<cctype>
#include<cstdlib>
#include<queue>
#include<deque>
#include<stack>
#include<vector>
#include<algorithm>
#include<utility>
#include<bitset>
#include<set>
#include<map>
#define ll long long
#define db double
#define INF 1000000000000000000ll
#define inf 1000000001
#define ldb long double
#define pb push_back
#define put_(x) printf("%d ",x);
#define get(x) x=read()
#define gt(x) scanf("%d",&x)
#define gi(x) scanf("%lf",&x)
#define put(x) printf("%d\n",x)
#define putl(x) printf("%lld\n",x)
#define rep(p,n,i) for(int i=p;i<=n;++i)
#define go(x) for(int i=lin[x],tn=ver[i];i;tn=ver[i=nex[i]])
#define pii pair<int,int>
#define mk make_pair
#define P 1000000007ll
#define gf(x) scanf("%lf",&x)
#define pf(x) ((x)*(x))
#define uint unsigned long long
#define ui unsigned
#define EPS 1e-10
#define sq sqrt
#define S second
#define F first
#define mod 998244353
#define r(x) c[x].r
#define l(x) c[x].l
#define cc(x) c[x].cc
#define mx2(x) t[x].mx2
#define max(x,y) ((x)<(y)?y:x)
using namespace std;
char *fs,*ft,buf[1<<15];
inline char gc()
{
return (fs==ft&&(ft=(fs=buf)+fread(buf,1,1<<15,stdin),fs==ft))?0:*fs++;
}
inline int read()
{
int x=0,f=1;char ch=gc();
while(ch<'0'||ch>'9'){if(ch=='-')f=-1;ch=gc();}
while(ch>='0'&&ch<='9'){x=x*10+ch-'0';ch=gc();}
return x*f;
}
const int MAXN=1000010;
int T;
int p,B,top,top1;
int inv[MAXN];
struct wy
{
int x,y;
}s[MAXN],w[MAXN];
inline int cmp(wy a,wy b){return a.x<b.x;}
int main()
{
//freopen("1.in","r",stdin);
//freopen("1.out","w",stdout);
T=read();
while(T--)
{
p=read();top1=top=0;
if(p==2){printf("0\n");continue;}
if(p==3){printf("1\n");printf("2 2\n");continue;}
B=(int)sqrt(p*1.0);
int i=3;inv[1]=1;
inv[2]=p-(ll)inv[p%2]*(p/2)%p;
s[top=1].x=2;s[top].y=inv[2];
w[++top1].x=inv[2];w[top1].y=2;
while(i<p)
{
inv[i]=p-(ll)inv[p%i]*(p/i)%p;
if(inv[i]<=s[top].y)
{
if(i==inv[i]){s[++top].x=i,s[top].y=inv[i];break;}
if(i==s[top].y)break;
s[++top].x=i,s[top].y=inv[i];
w[++top1].x=inv[i];w[top1].y=i;
}
++i;
}
printf("%d\n",top+top1);
rep(1,top,i)printf("%d %d\n",s[i].x,s[i].y);
for(int i=top1;i>=1;--i)printf("%d %d\n",w[i].x,w[i].y);
}
return 0;
}
code
//#include<bits/stdc++.h>
#include<iostream>
#include<cstdio>
#include<ctime>
#include<cctype>
#include<queue>
#include<deque>
#include<stack>
#include<iostream>
#include<iomanip>
#include<cstdio>
#include<cstring>
#include<string>
#include<ctime>
#include<cmath>
#include<cctype>
#include<cstdlib>
#include<queue>
#include<deque>
#include<stack>
#include<vector>
#include<algorithm>
#include<utility>
#include<bitset>
#include<set>
#include<map>
#define ll long long
#define db double
#define INF 1000000000000000000ll
#define inf 100000000000000000ll
#define ldb long double
#define pb push_back
#define put_(x) printf("%d ",x);
#define get(x) x=read()
#define gt(x) scanf("%d",&x)
#define gi(x) scanf("%lf",&x)
#define put(x) printf("%d\n",x)
#define putl(x) printf("%lld\n",x)
#define rep(p,n,i) for(int i=p;i<=n;++i)
#define go(x) for(int i=lin[x],tn=ver[i];i;tn=ver[i=nex[i]])
#define pii pair<int,int>
#define mk make_pair
#define P 1000000007ll
#define gf(x) scanf("%lf",&x)
#define pf(x) ((x)*(x))
#define uint unsigned long long
#define ui unsigned
#define EPS 1e-10
#define sq sqrt
#define S second
#define F first
#define mod 998244353
#define r(x) c[x].r
#define l(x) c[x].l
#define cc(x) c[x].cc
#define mx2(x) t[x].mx2
#define max(x,y) ((x)<(y)?y:x)
using namespace std;
char *fs,*ft,buf[1<<15];
inline char gc()
{
return (fs==ft&&(ft=(fs=buf)+fread(buf,1,1<<15,stdin),fs==ft))?0:*fs++;
}
inline int read()
{
int x=0,f=1;char ch=gc();
while(ch<'0'||ch>'9'){if(ch=='-')f=-1;ch=gc();}
while(ch>='0'&&ch<='9'){x=x*10+ch-'0';ch=gc();}
return x*f;
}
const int MAXN=2010;
ll a[MAXN][MAXN],ans;
int n,m1,m2,cnt,root,xx,yy,cx,cy;
struct V{ll t[MAXN<<2];int l,r;}c[MAXN<<1];
inline void build1(int x,int rt,int L,int R,int pos)
{
if(L==R){c[x].t[rt]=a[pos][L];return;}
int mid=(L+R)>>1;
build1(x,rt<<1,L,mid,pos);
build1(x,rt<<1|1,mid+1,R,pos);
c[x].t[rt]=max(c[x].t[rt<<1],c[x].t[rt<<1|1]);
}
inline void pushup(int lp,int rp,int x,int rt,int L,int R)
{
c[x].t[rt]=max(c[lp].t[rt],c[rp].t[rt]);
if(L==R)return;
int mid=(L+R)>>1;
pushup(lp,rp,x,rt<<1,L,mid);
pushup(lp,rp,x,rt<<1|1,mid+1,R);
}
inline void build(int L,int R,int &p)
{
p=++cnt;
if(L==R){build1(p,1,1,n,L);return;}
int mid=(L+R)>>1;
build(L,mid,l(p));
build(mid+1,R,r(p));
pushup(l(p),r(p),p,1,1,n);
}
inline void ask1(int x,int rt,int L,int R)
{
if(cy<=L&&yy>=R){ans=max(ans,c[x].t[rt]);return;}
int mid=(L+R)>>1;
if(cy<=mid)ask1(x,rt<<1,L,mid);
if(yy>mid)ask1(x,rt<<1|1,mid+1,R);
}
inline void ask(int L,int R,int p)
{
if(cx<=L&&xx>=R){ask1(p,1,1,n);return;}
int mid=(L+R)>>1;
if(cx<=mid)ask(L,mid,l(p));
if(xx>mid)ask(mid+1,R,r(p));
return;
}
int main()
{
//freopen("1.in","r",stdin);
n=read();
m1=read();m2=read();
rep(1,m1,i)
{
int x,y,z;
x=read();y=read();xx=read();yy=read();z=read();
a[x][y]+=z;a[xx+1][y]-=z;a[x][yy+1]-=z;a[xx+1][yy+1]+=z;
}
rep(1,n,i)rep(1,n,j)a[i][j]+=a[i-1][j]+a[i][j-1]-a[i-1][j-1];
/*rep(1,n,i)
{
rep(1,n,j)
cout<<a[i][j]<<' ';
cout<<endl;
}*/
build(1,n,root);
rep(1,m2,i)
{
cx=read();cy=read();xx=read();yy=read();
ans=0;ask(1,n,root);
printf("%lld\n",ans);
}
return 0;
}
- J 看不懂题目 我是废物。
题目