C++ 推斷一棵二叉樹是否對稱
阿新 • • 發佈:2017-08-18
ack iostream 們的 log data 簡單 src -a nbsp
mySymmetric(leftChild->right,rightChild->left)是計算下圖中藍色方框的部分是否關於對稱軸對稱:
一棵二叉樹對稱,就是說它假設以根為軸,翻轉過去一樣。例如以下圖所看到的,以虛線為軸。把左邊翻轉到右邊,各頂點及頂點中的值一一相應。
註意,它並不要求單獨看子樹的時候子樹也是對稱的,例如以下圖,單獨看左子樹時,左子樹是不正確稱的,單獨看右子樹時。右子樹也是不正確稱的,但這棵本身是對稱的。
要推斷一棵二叉樹是否對稱,那就是推斷它的左子樹翻轉過去是否和右子樹一樣,註意這裏的“一樣”包含了值也一樣。
以下給出代碼,當中的樣例中的樹,就是第一張圖中的那棵樹:
#include <iostream> using namespace std; struct TreeNode { int val; TreeNode *left; TreeNode *right; TreeNode(int x) : val(x), left(NULL), right(NULL) {} }; class Solution { public: bool isSymmetric(TreeNode *root) { if(root==NULL)//假設樹為空,對稱。返回 return true; return mySymmetric(root->left,root->right);//否則推斷以root為根時。左子樹翻轉後是否和右子樹一樣 } bool mySymmetric(TreeNode *leftChild,TreeNode *rightChild) { if(leftChild==NULL && rightChild==NULL)//左右子樹都為空,對稱 return true; else if(leftChild!=NULL && rightChild==NULL || leftChild==NULL && rightChild!=NULL){//一個空一個非空,則不正確稱 return false; }else{ //否則,再推斷 if(mySymmetric(leftChild->left,rightChild->right) //(1)leftChild的左子樹和rightChild的右子樹對稱嗎? && mySymmetric(leftChild->right,rightChild->left) //(2)leftChild的右子樹和rightChild的左子樹對稱嗎? && leftChild->val==rightChild->val){ //(3)leftChild和rightChild的值一樣嗎? return true;//三個條件都滿足,對稱 }else return false;//否則不正確稱 } } }; int main() { //樣例 TreeNode root(1); TreeNode leftChild(2); TreeNode rightChild(2); TreeNode leftLeftChild(3); TreeNode leftRightChild(4); TreeNode rightLeftChild(4); TreeNode rightRightChild(3); root.left=&leftChild; root.right=&rightChild; leftChild.left=&leftLeftChild; leftChild.right=&leftRightChild; rightChild.left=&rightLeftChild; rightChild.right=&rightRightChild; Solution s; if(true==s.isSymmetric(&root)) cout<<"對稱"<<endl; else cout<<"不正確稱"<<endl; system("pause"); return 0; }
以下通過幾個簡單的圖來說明一下。
mySymmetric(leftChild->left,rightChild->right)是計算下圖中藍色方框的部分是否關於對稱軸對稱:mySymmetric(leftChild->right,rightChild->left)是計算下圖中藍色方框的部分是否關於對稱軸對稱:
別忘了還要比較它們的值是否相等~
C++ 推斷一棵二叉樹是否對稱