数据结构

再智障错误我每天打一个数据结构

第一次线段树

第二次手打堆

第三次左偏树

第四次K-Dtree

第五次虚树

第六次splay

第七次LCT

第八次treap

第九次树套树

第十次就去死吧

 

最近我在搞什么鬼。

今天T2一个bool变量忘了清零,T3所有变量都忘了清零,帮别人debug也把函数错了;

昨天T1和T3爆空间,前天mod应该是maxnn写成了maxn,debug两小时;

大前天双向边开成了单向。

再前一天把出栈的标记放在了括号外面。

再这样考个铲铲,天天爆零。

 

第一次:POJ1062昂贵的聘礼单向边开成了双向。洛谷P3373线段树2

//Serene
#include<algorithm>
#include<iostream>
#include<cstring>
#include<cstdlib>
#include<cstdio>
#include<cmath>
using namespace std;
const int maxn=1e5+10;
long long n,m,mod,v[maxn];

struct Node{
	long long l,r,sum,laz[2];
}node[4*maxn];

long long aa;char cc;
long long read() {
	aa=0;cc=getchar();
	while(cc<'0'||cc>'9') cc=getchar();
	while(cc>='0'&&cc<='9') aa=aa*10+cc-'0',cc=getchar();
	return aa;
}

void ud(int pos) {
	if(node[pos].l==node[pos].r) {
		node[pos].laz[0]=1;node[pos].laz[1]=0;
		return;
	}
	if(!node[pos].laz[1]&&node[pos].laz[0]==1) return;
	int x;
	if(node[pos].laz[0]!=1) {
		x=node[pos].laz[0];
		node[pos<<1].laz[0]=node[pos<<1].laz[0]*x%mod;
		node[pos<<1].laz[1]=node[pos<<1].laz[1]*x%mod;
		node[pos<<1|1].laz[0]=node[pos<<1|1].laz[0]*x%mod;
		node[pos<<1|1].laz[1]=node[pos<<1|1].laz[1]*x%mod;
		node[pos<<1].sum=node[pos<<1].sum*x%mod;
		node[pos<<1|1].sum=node[pos<<1|1].sum*x%mod;
	}
	if(node[pos].laz[1]) {
		x=node[pos].laz[1];
		node[pos<<1].laz[1]=(node[pos<<1].laz[1]+x)%mod;
		node[pos<<1|1].laz[1]=(node[pos<<1|1].laz[1]+x)%mod;
		node[pos<<1].sum=(node[pos<<1].sum+x*(node[pos<<1].r-node[pos<<1].l+1))%mod;
		node[pos<<1|1].sum=(node[pos<<1|1].sum+x*(node[pos<<1|1].r-node[pos<<1|1].l+1))%mod;
	}
	node[pos].laz[0]=1;node[pos].laz[1]=0;
}

void bld(int pos,int l,int r) {
	node[pos].l=l;node[pos].r=r;
	node[pos].laz[0]=1;
	if(l==r) {
		node[pos].sum=v[l];
		return;
	}
	int mid=(l+r)>>1;
	bld(pos<<1,l,mid);
	bld(pos<<1|1,mid+1,r);
	node[pos].sum=(node[pos<<1].sum+node[pos<<1|1].sum)%mod;
}

void chge(int pos,int l,int r,int p,long long x) {
	if(node[pos].l==l&&node[pos].r==r) {
		if(p) {
			node[pos].sum=(node[pos].sum+x*(node[pos].r-node[pos].l+1)%mod)%mod;
			node[pos].laz[1]=(node[pos].laz[1]+x)%mod;
		}
		else {
			node[pos].sum=node[pos].sum*x%mod;
			node[pos].laz[0]=node[pos].laz[0]*x%mod;
			node[pos].laz[1]=node[pos].laz[1]*x%mod;
		}
		return;
	}
	ud(pos);
	int mid=(node[pos].l+node[pos].r)>>1;
	if(r<=mid) chge(pos<<1,l,r,p,x);
	else if(l>mid) chge(pos<<1|1,l,r,p,x);
	else chge(pos<<1,l,mid,p,x),chge(pos<<1|1,mid+1,r,p,x);
	node[pos].sum=(node[pos<<1].sum+node[pos<<1|1].sum)%mod;
}

long long q(int pos,int l,int r) {
	ud(pos);
	if(node[pos].l==l&&node[pos].r==r) return node[pos].sum;
	int mid=(node[pos].l+node[pos].r)>>1;
	if(r<=mid) return q(pos<<1,l,r);
	else if(l>mid) return q(pos<<1|1,l,r);
	else return (q(pos<<1,l,mid)+q(pos<<1|1,mid+1,r))%mod;
}

int main() {
	n=read();m=read();mod=read();
	for(int i=1;i<=n;++i) v[i]=read()%mod;
	bld(1,1,n);
	long long op,x,y,z;
	for(int i=1;i<=m;++i) {
		op=read();x=read();y=read();
		if(op==1||op==2) {
			z=read();
			chge(1,x,y,op-1,z%mod);
		}
		else printf("%lld\n",q(1,x,y));
	}
	return 0;
}
/*
8 10 571373
5929 7152 8443 6028 8580 5449 8473 4237 
2 4 8 4376
1 2 8 9637
2 2 6 7918
2 5 8 5681
3 2 8
1 1 5 6482
3 1 5
1 5 8 8701
2 5 8 7992
2 5 8 7806
*/

  

第二次:bzoj1624 寻宝之路maxm写成maxn。洛谷P3378 堆

//Serene
#include<algorithm>
#include<iostream>
#include<cstring>
#include<cstdlib>
#include<cstdio>
#include<cmath>
using namespace std;
const int maxn=1e6+10;
int n,d[maxn],tot;

int aa,ff;char cc;
int read() {
	aa=0;cc=getchar();ff=1;
	while(cc<'0'||cc>'9') {
		if(cc=='-')ff=-1;
		cc=getchar();
	}
	while(cc>='0'&&cc<='9') aa=aa*10+cc-'0',cc=getchar();
	return aa*ff;
}

void add(int x) {
	d[++tot]=x;
	int pos=tot,fa=pos>>1;
	while(fa&&x<d[fa]) {
		swap(d[fa],d[pos]);
		pos=fa;fa=pos>>1;
	}
}

void del() {
	swap(d[1],d[tot]);d[tot--]=0x3f3f3f3f;
	int pos=1,son;
	while((pos<<1)<=tot&&min(d[pos<<1],d[pos<<1|1])<d[pos]) {
		son=pos<<1;
		if(d[pos<<1|1]<d[son]) son++;
		swap(d[pos],d[son]);
		pos=son;
	}
}

int main() {
	n=read();
	memset(d,0x3f3f3f,sizeof(d));
	int op,x;
	for(int i=1;i<=n;++i) {
		op=read();
		if(op==1) {
			x=read();
			add(x);
		}
		else if(op==2) printf("%d\n",d[1]);
		else del();
	}
	return 0;
}

  

第三次:TCPThree_C杯忘开long long。洛谷P3377左偏树(可并堆)

//Serene
#include<algorithm>
#include<iostream>
#include<cstring>
#include<cstdlib>
#include<cstdio>
#include<cmath>
using namespace std;
const int maxn=1e6+10;
int n,m;
int fa[maxn],num[maxn],son[maxn][2],len[maxn];
bool ud[maxn];

int aa;char cc;
int read() {
	aa=0;cc=getchar();
	while(cc<'0'||cc>'9') cc=getchar();
	while(cc>='0'&&cc<='9') aa=aa*10+cc-'0',cc=getchar();
	return aa;
}

int find(int x) {
	return x==fa[x]? x:fa[x]=find(fa[x]);
}

int merge(int x,int y) {
	if(!x||!y) return x+y;
	if(num[x]>num[y]||(num[x]==num[y]&&x>y)) swap(x,y);
	son[x][1]=merge(son[x][1],y);
	fa[son[x][1]]=x;
	if(len[son[x][1]]>len[son[x][0]]) swap(son[x][0],son[x][1]);
	len[x]=len[son[x][1]]+1;
	return x;
}

void del(int x) {
	if(!len[x]) {
		printf("-1\n");	return ;
	}
	x=find(x);
	printf("%d\n",num[x]);
	fa[son[x][0]]=son[x][0]; fa[son[x][1]]=son[x][1];
	fa[x]=merge(son[x][0],son[x][1]);
	len[x]=0;son[x][0]=son[x][1]=0;
	ud[x]=1;
}

int main() {
	n=read();m=read();
	for(int i=1;i<=n;++i) {
		num[i]=read();
		fa[i]=i; len[i]=1;
	}
	int op,x,y;
	for(int i=1;i<=m;++i) {
		op=read();
		if(op==1) {
			x=read();y=read();
			if(!len[x]||!len[y]) continue;
			x=find(x);y=find(y);
			if(x==y) continue;
			merge(x,y);
		}
		else {
			x=read();
			del(x);
		}
	}
	return 0;
}

  附上对拍的rand:

//Serene
#include<algorithm>
#include<iostream>
#include<cstring>
#include<cstdlib>
#include<cstdio>
#include<cmath>
#include<ctime>
using namespace std;
const int n=10,m=10;

int main() {
	srand((unsigned)time(NULL));
	printf("%d %d\n",n,m);
	int x,y;
	for(int i=1;i<=n;++i) printf("%d ",rand()%n+1);
	printf("\n");
	for(int i=1;i<=m;++i) {
		x=rand()%n+1;y=rand()%n+1;
		if(rand()%2) printf("1 %d %d\n",x,y);
		else printf("2 %d\n",x);
	}
	return 0;
}

  

 

第四次:9.22考试乘号打成加号,K-D tree,bzoj4154

以每个节点的 DFS 序作为横坐标,深度作为纵坐标,那么就可以把一棵树放在坐标系里。

然后我打了一个诡异的像线段树的K-D tree,就跑得贼快(然而我用了整整一个下午debug)。。。

//Serene
#include<algorithm>
#include<iostream>
#include<cstring>
#include<cstdlib>
#include<cstdio>
#include<cmath>
using namespace std;
const int maxn=1e5+10,mod=1e9+7;
int T,n,c,qaq,fa[maxn];long long ans;

int aa;char cc;
int read() {
	aa=0;cc=getchar();
	while(cc<'0'||cc>'9') cc=getchar();
	while(cc>='0'&&cc<='9') aa=aa*10+cc-'0',cc=getchar();
	return aa;
}

int fir[maxn],to[maxn],nxt[maxn],e=0;
void add(int x,int y) {
	to[++e]=y;nxt[e]=fir[x];fir[x]=e;
}

int dep[maxn],size[maxn],son[maxn];
void dfs1(int pos) {
	dep[pos]=dep[fa[pos]]+1;
	size[pos]=1; int y,z;
	for(y=fir[pos];y;y=nxt[y]) {
		dfs1(z=to[y]);
		size[pos]+=size[z];
		if(size[z]>size[son[pos]]) son[pos]=z;
	}
}

int id[maxn],end[maxn],tot_id;
int pyh[maxn];
void dfs2(int pos) {
	id[pos]=++tot_id; pyh[tot_id]=pos;
	if(!son[pos]) {end[pos]=id[pos];return ;}
	dfs2(son[pos]); int y,z;
	for(y=fir[pos];y;y=nxt[y]) {
		if((z=to[y])==son[pos]) continue;
		dfs2(z);
	}
	end[pos]=tot_id;
}

struct Node{
	int l,r,d[2];long long cl;
}node[4*maxn];

void bld(int pos,int l,int r) {
	node[pos].l=l;node[pos].r=r;
	if(l==r) {
		node[pos].cl=1;
		node[pos].d[0]=node[pos].d[1]=dep[pyh[l]];
		return ;
	}
	int mid=(l+r)>>1;
	bld(pos<<1,l,mid); bld(pos<<1|1,mid+1,r);
	node[pos].d[0]=min(node[pos<<1].d[0],node[pos<<1|1].d[0]);
	node[pos].d[1]=max(node[pos<<1].d[1],node[pos<<1|1].d[1]);
}

void pd(int pos) {
	if(!node[pos].cl||node[pos].l==node[pos].r) return;
	node[pos<<1].cl=node[pos].cl;node[pos<<1|1].cl=node[pos].cl;
	node[pos].cl=0;
}

long long q(int pos,int x) {
	if(node[pos].l==node[pos].r) return node[pos].cl;
	pd(pos);
	int mid=(node[pos].l+node[pos].r)>>1;
	if(x<=mid) return q(pos<<1,x);
	return q(pos<<1|1,x);
}

void chge(int pos,int l,int r,int d0,int d1,int cl) {
	if(node[pos].l==l&&node[pos].r==r) {
		if(node[pos].d[0]>=d0&&node[pos].d[1]<=d1) node[pos].cl=cl;
		else if(node[pos].l!=node[pos].r){
			pd(pos);
			int mid=(node[pos].l+node[pos].r)>>1;
			if(node[pos<<1].d[0]<=d1&&node[pos<<1].d[1]>=d0) chge(pos<<1,l,mid,d0,d1,cl);
			if(node[pos<<1|1].d[0]<=d1&&node[pos<<1|1].d[1]>=d0) chge(pos<<1|1,mid+1,r,d0,d1,cl);
		}
		return;
	}
	pd(pos);
	int mid=(node[pos].l+node[pos].r)>>1;
	if(r<=mid) chge(pos<<1,l,r,d0,d1,cl);
	else if(l>mid) chge(pos<<1|1,l,r,d0,d1,cl);
	else chge(pos<<1,l,mid,d0,d1,cl),chge(pos<<1|1,mid+1,r,d0,d1,cl);
}

void clear() {
	memset(fir,0,sizeof(fir));
	memset(son,0,sizeof(son));
	memset(node,0,sizeof(node));
	e=0; tot_id=0; ans=0;
}

int main() {
	T=read();
	while(T--) {
		n=read();c=read();qaq=read();
		clear(); int a,l;
		for(int i=2;i<=n;++i) fa[i]=read(),add(fa[i],i);
		dfs1(1); dfs2(1); bld(1,1,n);
		for(int i=1;i<=qaq;++i) {
			a=read();l=read();c=read();
			if(!c) (ans+=(long long)i*q(1,id[a]))%=mod;
			else chge(1,id[a],end[a],dep[a],dep[a]+l,c);
		}
		printf("%lld\n",ans);
	}
	return 0;
}
/*
1
10 5 5
1 1 2 3 4 5 4 8 2 
1 9 2
6 2 1
5 10 1
2 2 2
7 1 0
*/

 给出对拍的rand:

//Serene
#include<algorithm>
#include<iostream>
#include<cstring>
#include<cstdlib>
#include<cstdio>
#include<cmath>
#include<ctime>
using namespace std;
const int n=10,c=50,q=5;

int main() {
	srand((unsigned)time(NULL));
	cout<<"1\n";
	cout<<n<<" "<<c<<" "<<q<<"\n";
	cout<<"1 ";
	int x,y,z;
	for(int i=3;i<=n;++i) {
		x=rand()%(i-1)+1;
		cout<<x<<" ";
	}
	cout<<"\n";
	for(int i=1;i<=q;++i) {
		x=rand()%n+1;y=rand()%n+1;z=rand()%(c+1);
		cout<<x<<" "<<y<<" "<<z<<"\n";
	}
	return 0;
}

  
我觉得这篇博文将是我博客里面最长的一篇

 

第五次:9.26考试数组开小了,虚树,bzoj3991

//Serene
#include<algorithm>
#include<iostream>
#include<cstring>
#include<cstdlib>
#include<cstdio>
#include<cmath>
#include<set>
using namespace std;
const int maxn=1e5+10;
int n,m;long long ans;
bool ins[maxn];
set<int> G;
set<int>::iterator it;

long long aa;char cc;
long long read() {
	aa=0;cc=getchar();
	while(cc<'0'||cc>'9') cc=getchar();
	while(cc>='0'&&cc<='9') aa=aa*10+cc-'0',cc=getchar();
	return aa;
}

int fir[maxn],nxt[2*maxn],to[2*maxn],e=0;
long long v[2*maxn];
void add(int x,int y,long long z) {
	to[++e]=y;nxt[e]=fir[x];fir[x]=e;v[e]=z;
	to[++e]=x;nxt[e]=fir[y];fir[y]=e;v[e]=z;
}

int dep[maxn],size[maxn],son[maxn],fa[maxn];
long long sum[maxn];
void dfs1(int pos,int d) {
	size[pos]=1;dep[pos]=d;
	int y,z;
	for(y=fir[pos];y;y=nxt[y]) {
		if((z=to[y])==fa[pos]) continue;
		fa[z]=pos; sum[z]=sum[pos]+v[y];
		dfs1(z,d+1);	size[pos]+=size[z];
		if(size[z]>size[son[pos]]) son[pos]=z;
	}
}

int id[maxn],num[maxn],top[maxn],tot_id;
void dfs2(int pos,int tp) {
	id[pos]=++tot_id; num[tot_id]=pos; top[pos]=tp;
	if(!son[pos]) return;
	dfs2(son[pos],tp);
	int y,z;
	for(y=fir[pos];y;y=nxt[y]) {
		z=to[y]; if(z==fa[pos]||z==son[pos]) continue;
		dfs2(z,z);
	}
}

int lca(int x,int y) {
	while(top[x]!=top[y]) {
		if(dep[top[x]]<dep[top[y]]) swap(x,y);
		x=fa[top[x]];
	}
	if(dep[x]>dep[y]) swap(x,y);
	return x;
}

long long f(int x) {
	int l,r;
	it=G.find(id[x]); it++;
	if(it==G.end()) it=G.begin(); l=num[*it];
	it=G.find(id[x]); if(it==G.begin()) it=G.end();
	it--; r=num[*it];
	return 2*(sum[lca(l,x)]+sum[lca(x,r)]-sum[x]-sum[lca(l,r)]);
}

int main() {
	n=read();m=read();
	int x,y;long long z;
	for(int i=1;i<n;++i) {
		x=read();y=read();z=read();
		add(x,y,z);
	}
	dfs1(1,1);dfs2(1,1);
	for(int i=1;i<=m;++i) {
		x=read();
		if(ins[x]) {ans+=f(x); G.erase(id[x]);}
		else {G.insert(id[x]); ans-=f(x);}
		ins[x]^=1; printf("%lld\n",ans);
	}
	return 0;
}

  天哪,wjx说到第十次要开一个虫洞去FFT,瑟瑟发抖。

 

第六次:9.29考试没开long long。Splay,bzoj1588

//Serene
#include<algorithm>
#include<iostream>
#include<cstring>
#include<cstdlib>
#include<cstdio>
#include<cmath>
using namespace std;
const int maxn=32767+10,INF=1e8;
int n,ans,root=0;

int aa,ff;char cc;
int read() {
	aa=0;ff=1;cc=getchar();
	while(cc<'0'||cc>'9') {
		if(cc=='-') ff=-1;
		cc=getchar();
	}
	while(cc>='0'&&cc<='9') aa=aa*10+cc-'0',cc=getchar();
	return aa*ff;
}

struct Node{
	int son[2],fa,num;
}node[maxn];
int tot=0;

void rotate(int pos) {
	int x=node[pos].fa,y=node[x].fa;
	int p=node[x].son[1]==pos,pp=node[y].son[1]==x;
	node[x].son[p]=node[pos].son[!p];
	node[pos].son[!p]=x;
	node[pos].fa=y;node[x].fa=pos;
	if(node[x].son[p]) node[node[x].son[p]].fa=x;
	if(root==x) root=pos;
	else node[y].son[pp]=pos;
}

void splay(int pos) {
	int x=node[pos].fa,y=node[x].fa;
	while(pos!=root) {
		x=node[pos].fa,y=node[x].fa;
		if(x!=root) {
			if(node[x].son[0]==pos ^ node[y].son[0]==x) rotate(pos);
			else rotate(x);
		}
		rotate(pos);
	}
}

int q(int pos,int x) {
	if(!pos) return INF;
	int rs=abs(node[pos].num-x);
	if(!rs) return 0;
	if(node[pos].num>x) return rs=min(rs,q(node[pos].son[0],x));
	else return rs=min(rs,q(node[pos].son[1],x));
}

void chge(int& pos,int x,int f) {
	if(!pos) {pos=tot;node[tot].fa=f;return;}
	if(x<node[pos].num) chge(node[pos].son[0],x,pos);
	else chge(node[pos].son[1],x,pos);
}

void add(int x) {
	node[++tot].num=x;
	chge(root,x,0);
	splay(tot);
}

int main() {
	n=read();int x,y=1;
	for(int i=1;i<=n;++i) {
		x=read();
		if(i!=1) ans+=(y=q(root,x)); else ans+=x;
		if(y) add(x);
	}
	printf("%d",ans);
	return 0;
}
/*
5
2
3
3
1
7
*/

  

弱者就是会被欺负呀
posted @ 2017-09-15 19:12  shixinyi  阅读(290)  评论(0编辑  收藏  举报