pat-1143

コード1にはポイントがあります。REランタイムタイムアウト。このメソッドは、中間次数がわかっている一般的なツリーに使用できます。

#include<iostream>
#include<map>
#include<vector>
using namespace std;
int main()
{int m,n;
cin>>m>>n;
//如果是二叉树的话就不需要中序了只要抓住按值大小就是中序 
vector<int> pre;
map<int,bool>cp;
pre.resize(n+1);
for(int i=1;i<=n;i++)
{scanf("%d",&pre[i]);
cp[pre[i]]=true;
}
//与这个 i重复声明所以一开始i弄成了0不要重用 
for(int i=0;i<m;i++)
{
	int p1,p2;
	cin>>p1>>p2;
	//此处i应该弄为全局变量因为后面要用到,每一个要用到的变量是局部还是全局要分清不一样(注意) 
	int j=1; 
	for(j;j<=n;j++)
	if(pre[j]>=p1&&pre[j]<=p2||pre[j]<=p1&&pre[j]>=p2) break;

	if(cp[p1]==false&&cp[p2]==false) printf("ERROR: %d and %d are not found.\n",p1,p2);
	else if(cp[p1]==true&&cp[p2]==false||cp[p1]==false&&cp[p2]==true) printf("ERROR: %d is not found.\n",cp[p1]==0?p1:p2);
	else if(pre[j]>p1&&pre[j]<p2||pre[j]<p1&&pre[j]>p2)printf("LCA of %d and %d is %d.\n",p1,p2,pre[j]);
    else if(pre[j]==p1||pre[j]==p2) printf("%d is an ancestor of %d.\n",pre[j]==p1?p1:p2,pre[j]==p1?p2:p1);
}
return 0;

}

 BSTに対して直接

#include<iostream>
#include<map>
#include<vector>
#include<algorithm>
using namespace std;
int m,n;
//pos存入的是中序的位置 
map<int ,int> pos;
vector<int> pre,in;
void lca(int preroot,int inll,int inrr,int ll,int rr)
{  //END  考虑一个节点的情况
   //必须要把输入接口放到外面否则每次递归都会再输入导致错误 没有考虑递归对输入的影响 
    if(inll>inrr) return;
	
	 int inpos=pos[pre[preroot]];
	if(pos[ll]==0&&pos[rr]==0)printf("ERROR: %d and %d are not found.\n",ll,rr);
	else if(pos[ll]==0||pos[rr]==0)printf("ERROR: %d is not found.\n",pos[ll]==0?ll:rr);
    
     //in,pre,入时要都从1开始入 
     //两边不一定谁在那一边都要写上 
     else if(pos[ll]<inpos&&pos[rr]>inpos||pos[ll]>inpos&&pos[rr]<inpos) printf("LCA of %d and %d is %d.\n",ll,rr,in[inpos]);
     else if(pos[ll]<inpos&&pos[rr]<inpos) lca(preroot+1,inll,inpos-1,ll,rr);
     else if(pos[ll]>inpos&&pos[rr]>inpos) lca(preroot+inpos-inll+1,inpos+1,inrr,ll,rr);
     //ll打成11我也是醉了(注意) 
     else if(pos[ll]==inpos) printf("%d is an ancestor of %d.\n",ll,rr);
     else if(pos[rr]==inpos) printf("%d is an ancestor of %d.\n",rr,ll);
	
}
int main()
{
	scanf("%d %d",&m,&n); 
	pre.resize(n+1);
	in.resize(n+1);
	for(int i=1;i<=n;i++)
	{
		scanf("%d",&pre[i]);
		//没有两次出入注意不能放一块 注意 
		in[i]=pre[i];
	}
	
	sort(in.begin(),in.end());
	//debug
	//for(int i=0;i<in.size();i++)
	//printf("%d ",in[i]);
	//没有建立键值对
	for(int i=1;i<=n;i++)
	pos[in[i]]=i; 
	for(int i=0;i<m;i++)
	{  int ll,rr;
	   scanf("%d %d",&ll,&rr);
		lca(1,1,n,ll,rr);
	}
	return 0;
}
 

総括する

1.最初の方法は一般的なツリーに使用できます。プレオーダーとミドルオーダーがわかっている場合、2番目の方法はバイナリツリーのルートノードに関連するノードを直接見つけることができます。

2. dfs再帰と入力の競合により、入力を再帰的にループすることはできません。同時に、入力処理の1行に2つの入力を含めることはできないことに注意してください。

3.グローバル変数iのカウントローカルiが必要であり、結果が競合します。変数を使用する場合、グローバルではなくローカルでのみ機能するかどうかを明確にし、上記の変数と競合しないようにする必要があります。

4.ここでは、キーと値のペアを使用して、存在するかどうかをマークします。

英語

番号

グローバル変数とローカル変数を要約すると明確に記録され、上記の変数と競合しないようにしてください

 

おすすめ

転載: blog.csdn.net/m0_45359314/article/details/112769140