每日一題---完全二叉樹的權值

在這裏插入圖片描述
在這裏插入圖片描述
這題看起來好像是在考樹的編碼,實際上和樹還真沒多大關係,但有一點一定要注意了,就是!完全二叉樹不一定是滿二叉樹(不一定每層都是2^n)!
第一次自己碼的時候,就當做滿二叉樹了,感覺還怪簡單,事後才知道錯了o(╥﹏╥)o,後來修正後,代碼還是有問題。。。
代碼如下:

#include<bits/stdc++.h>
using namespace std;

int main(){
	int n,h,k=0,sum=0;
	cin>>n;
	int a[100005],b[100005];
	int max=0;
	for(int i=0;i<n;i++){
		cin>>a[i];
	}
	for(int i=0;i<100005;i++){
		sum+=pow(2,i);
		if(n==sum){
			h=i;
			for(int m=0;m<h;m++){
		        for(int j=0;j<pow(2,m);j++){
			        b[k]+=a[j];
		        }
		        k++;
	        }
		}else if(n>sum&&n<sum+pow(2,i+1)){
			h=i+1;
			for(int m=0;m<i;m++){
				for(int j=0;j<pow(2,m);j++){
					b[k]+=a[j];
				}
				k++;
			}
			for(int p=n-sum;p<n;p++){
				b[k]+=a[p]
			}
		} 
	}
	for(int i=0;i<k;i++){
		if(b[max]<b[i]){
			max=i;
		}
	}
	cout<<max+1<<endl;
	return 0;
}

後來實在沒辦法,就參考了大神網友的代碼,如下:

#include<bits/stdc++.h>
using namespace std;
#define max 100005
int main(){
   int a[max],n;
   cin>>n;
   long long m=-max;//這裏的數據量還是比較大的,用int可能超限,用long long比較安全
   long long ans=0;
   for(int i=1;i<=n;i++){
   	cin>>a[i];
   }
   for(int i=1;(1<<(i-1))<=n;i++){//運用二進制的特徵把同一層的相加即可
   	  long long sum=0;
   	  for(int j=1<<(i-1);j<(1<<i);j++){
   	  	 sum+=a[j];
   	  }
   	  if(sum>m){
   	  	m=sum;
   	  	ans=i;
   	  }
   }
   cout<<ans<<endl;
   return 0;
}

我也不知道說啥,這可能就是大佬和菜鳥的差距吧,我還是第一次見將二進制數放入代碼中的神仙操作,簡直了!以後可以參考這樣的神仙做法,留着裝逼用。。。
*補充:n&(1<<i)是用來判斷n的第i位是否爲1。i>>1表示i右移1位,1<<i表示1左移i位,相當於第i位爲1,其他位爲0的整數。因此n&(1<<i)可以判斷整數n的第i位是否爲1。

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章