一个简化版的treap打版题,也当练练手。这个版来自百度百科。。。。。不知道数据大了效果怎么样。
主要是动态插入和查询。
#include<iostream>
#include<cstdio>
#include<ctime>
#include<cstdlib>
#define maxv 100005
using namespace std;
struct tree
{
	  int left,right;
	  int size,value,fix;
}node[maxv];
int n,m,regis[maxv],nume=1,root=-1;
void update(int k)
{
	  node[k].size=node[node[k].left].size+node[node[k].right].size+1;
}
void lturn(int &k)
{
	  int t=node[k].right;
	  node[k].right=node[t].left;
	  node[t].left=k;
	  node[t].size=node[k].size;
	  update(k);
	  k=t;
}
void rturn(int &k)
{
	  int t=node[k].left;
	  node[k].left=node[t].right;
	  node[t].right=k;
	  node[t].size=node[k].size;
	  update(k);
	  k=t;
}
void insert(int &x,int tkey)
{
	  if (x==-1)
	  {
		    nume++;x=nume;
		    node[nume].size=1;
		    node[nume].value=tkey;
		    node[nume].left=-1;
		    node[nume].right=-1;
		    node[nume].fix=rand();
	  }	
	  else
	  {
		    node[x].size++;
		    if (tkey<node[x].value) 
		    {
			      insert(node[x].left,tkey);
			      if (node[node[x].left].fix<node[x].fix) rturn(x);
		    }
		    else 
		    {
			      insert(node[x].right,tkey);
			      if (node[node[x].right].fix<node[x].fix) lturn(x);
		    }
	  }
}
int rank(int k,int x)
{
	  if (k==-1) return 0;
	  else
	  {
		  if (x<=node[node[k].left].size)
			    return rank(node[k].left,x);
		  else if (x>node[node[k].left].size+1)
			    return rank(node[k].right,x-node[node[k].left].size-1);
		  else return node[k].value;
	  }
}
int main()
{
	  srand(time(0));
	  while (scanf("%d%d",&n,&m)==2)
	  {
		    for (int i=1;i<=n;i++)
			    scanf("%d",®is[i]);
		    int k,l=1;
		    for (int i=1;i<=m;i++)
		    {
			      scanf("%d",&k);
			      while (l<=k) 
			      {
				        insert(root,regis[l]);
				        l++;
			      }
			     printf("%d\n",rank(root,i));
		    }
	  }
	  return 0;
}
                    
                
                
            
        
浙公网安备 33010602011771号