日韩性视频-久久久蜜桃-www中文字幕-在线中文字幕av-亚洲欧美一区二区三区四区-撸久久-香蕉视频一区-久久无码精品丰满人妻-国产高潮av-激情福利社-日韩av网址大全-国产精品久久999-日本五十路在线-性欧美在线-久久99精品波多结衣一区-男女午夜免费视频-黑人极品ⅴideos精品欧美棵-人人妻人人澡人人爽精品欧美一区-日韩一区在线看-欧美a级在线免费观看

歡迎訪問 生活随笔!

生活随笔

當前位置: 首頁 > 编程资源 > 编程问答 >内容正文

编程问答

坐下,这些都是二叉树的基本操作!

發布時間:2023/12/31 编程问答 38 豆豆
生活随笔 收集整理的這篇文章主要介紹了 坐下,这些都是二叉树的基本操作! 小編覺得挺不錯的,現在分享給大家,幫大家做個參考.

春招來了,辭了職在家里準備再找份實習工作。相信大家,尤其是大三、大四的同學都經常在招聘要求上看到這樣一條要求:熟悉常見的數據結構與算法。常見的數據結構通常有:鏈表二叉樹,如果要求再高點,可能會讓你實現紅黑樹AVL樹這種高級的數據結構。由此可見,數據結構與算法還是比較重要的,最近也是在復習這方面的知識。本篇為復習過程中遇到過的總結,同時也給各位跟我一樣準備面試的同學一份參考。另外,由于篇幅有限,本篇的重點在于二叉樹的常見算法以及實現。

常見的二叉樹實現代碼

之前寫過相關的文章,是關于如何創建及遍歷二叉樹的,這里不再贅述。提供鏈接給各位感興趣的小伙伴,點此跳轉

翻轉二叉樹

對于一棵二叉樹,翻轉它的左右子樹,如下圖所示:

下面來分析具體的實現思路:

  • 對于根結點為空的情況
    這種情況需要排除,因為null不是一個對象,不可能存在左右子樹并且可以翻轉的情況
  • 對于一棵只有一個根結點的二叉樹
    emmm,這種情況也可以翻轉,因為此時根結點左右子樹為null,交換左右子樹其實也就是在交換兩個null,理論上是翻轉了,但實際上我們看到的和沒有翻轉之前的結果是一樣的
  • 對于一棵具有兩個或兩個以上結點的二叉樹,此時二叉樹可以表示為如下的圖像:


可以看出,無論是只有左子樹還是只有右子樹都可以進行翻轉。這句話等價于,為空的子樹可以和不為空的子樹進行交換,也就是不對為空的子樹進行特殊處理

分析過程

其實這樣我們還是不知道二叉樹是如何翻轉的,我們可以用第一張圖的二叉樹為例子,看一下翻轉的具體過程。

  • 首先我們需要對根結點進行判空處理,在根結點不為空的情況下存在左右子樹(即使左右子樹為空),然后交換左右子樹;
  • 2. 把根結點的左子樹當成左子樹的根結點,對當前根結點進行判空處理,不為空時交換左右子樹;

    3. 把根結的右子樹當成右子樹的根結點,對當前根結點進行判空處理,不為空時交換左右子樹;

    4. 重復步驟23,最后二叉樹變為原來的鏡像結構,結果可以參考文章第一張示意圖。

    示例代碼

    根據上面的推理過程我們可以得出如下的代碼:

    function reverseTree(root){if( root !== null){[root.left, root.right] = [root.right, root.left]reverseTree(root.left)reverseTree(root.right)} } 復制代碼

    雖然推理過程比較復雜(也可能是寫的比較啰嗦。。),但是仔細觀察代碼,這和遍歷的代碼似乎也沒多大差別,只是把輸出結點變為了交換結點。

    判斷二叉樹是否完全對稱

    一棵左右完全對稱的二叉樹是這樣的:

    那到底如何判斷呢?

    • 根結點為空時,此時為一棵空二叉樹,滿足對稱條件(-_-||)
    • 只有一個根結點時,左右子樹都為null,滿足左右對稱條件
    • 只有兩個結點時,此時左右子樹必定有一個為空,不可能存在對稱的情況
    • 結點數在三個及三個以上時,二叉樹有對稱的可能。

    按照我們正常的思維,看對稱與否,首先看左邊,然后看右邊,最后比較左右是否相等。同時我們注意到,在二叉樹深度比較大的時候,我們光是比較左右是不夠的。可以觀察到,我們比較完左右以后還需要比較左的左右的右,比較左的右右的左

    分析過程

    這么看是比較繞,接下來我們來看圖分析:

  • 先比較根結點左右孩子
  • 左子樹根結點的左孩子右子樹根結點的右孩子進行比較
  • 左子樹根結點的右孩子右子樹根結點的左孩子進行比較
  • 重復以上過程...
  • 示例代碼

    function isSymmetrical(pRoot) {// write code hereif(!pRoot){return true}return funC(pRoot.left, pRoot.right) }function funC(left, right){if(!left){return right === null}if(!right){return false}if(left.val !== right.val){return false}return funC(left.right, right.left) && funC(left.left, right.right) } 復制代碼

    求二叉樹的深度

    分析過程

    • 只有一個根結點時,二叉樹深度為1
    • 只有左子樹時,二叉樹深度為左子樹深度加1
    • 只有右子樹時,二叉樹深度為右子樹深度加1
    • 同時存在左右子樹時,二叉樹深度為左右子樹中深度最大者加1

    示例代碼

    function deep(root){if(!root){return 0}let left = deep(root.left)let right = deep(root.right)return left > right ? left + 1 : right + 1 } 復制代碼

    求二叉樹的寬度

    二叉樹的寬度是啥?我把它理解為具有最多結點數的層中包含的結點數,比如下圖所示的二叉樹,其實它的寬度就是為4:

    分析過程

    根據上圖,我們如何算出二叉樹的寬度呢?其實有個很簡單的思路:

  • 算出第一層的結點數,保存
  • 算出第二層的結點數,保存一二層中較大的結點數
  • 重復以上過程
  • 示例代碼

    根據分析過程,我們可以利用隊列這種數據結構來實現這個算法,代碼如下:

    function width(root){if(!root){return 0}let queue = [root], max = 1, deep = 1while(queue.length){while(deep--){let temp = queue.shift()if(temp.left){queue.push(temp.left)}if(temp.right){queue.push(temp.right)}}deep = queue.lengthmax = max > deep ? max : deep}return max } 復制代碼

    重建二叉樹

    常見的遍歷

    • 前序遍歷: 前序遍歷首先訪問根結點然后遍歷左子樹,最后遍歷右子樹

    • 中序遍歷: 中序遍歷首先訪問左子樹然后遍歷根節點,最后遍歷右子樹

    • 后序遍歷: 后序遍歷首先遍歷左子樹,然后遍歷右子樹,最后訪問根結點

    題目描述

    根據前序遍歷產生的序列和中序遍歷產生的序列生成一顆二叉樹

    思路分析

    假如有這么一棵二叉樹:

    可以看出它前序遍歷序列為:8 6 5 7 10 9 11中序遍歷序列為:5 6 7 8 9 10 11 其中有個很明顯的特征,根結點的值為前序遍歷序列的第一個值,而且我們在中序遍歷序列中很容易看出,根結點左右兩邊的結點分別為構成左子樹右子樹的結點,所以我們可以得到一種解決問題的思路:

  • 獲取前序遍歷的第一個值,構建根結點
  • 生成左子樹的前序遍歷序列和中序遍歷序列
  • 生成右子樹的前序遍歷序列和中序遍歷序列
  • 重復以上過程...
  • 示例代碼

    function reConstructBinaryTree(pre, vin) {if(!pre || !vin || !pre.length || !vin.length){return null}let root = new TreeNode(pre[0]),tIndex = vin.indexOf(pre[0]),leftIn = [],leftPre = [],rightIn = [],rightPre = []for(let i = 0; i < tIndex; i++){leftIn.push(vin[i])leftPre.push(pre[i+1])}for(let i = tIndex+1; i < pre.length; i++){rightIn.push(vin[i])rightPre.push(pre[i])}//遞歸root.left = reConstructBinaryTree(leftPre, leftIn)root.right = reConstructBinaryTree(rightPre, rightIn)return root } 復制代碼

    以上思路、代碼有錯漏請在評論區指出!

    總結

    代碼部分來自牛客網--劍指offer,相應的題目也都可以在上面找到。不過在這期間,我也是找到了份實習工作,年后就要去搬磚了。既然找到了,春招就不參與了(春招難度比秋招難太多了)希望看這篇文章的同學們也能找到份合適的工作。

    總結

    以上是生活随笔為你收集整理的坐下,这些都是二叉树的基本操作!的全部內容,希望文章能夠幫你解決所遇到的問題。

    如果覺得生活随笔網站內容還不錯,歡迎將生活随笔推薦給好友。