【遞歸】樹形斷層判斷算法

場景node

        最近在接了個需求,其中有個樹形結構的勾選方式邏輯判斷比較複雜,斷層選擇須要進行邏輯判斷,什麼是斷層?看下圖給你解釋:算法

 

   

        黑色表明當前結點被勾選上,白色表明未勾選,上圖描述了斷層的邏輯,意思就是,有關聯的一條線上的節點,假如中間一個節點沒有勾選上,證實這就是斷層。this

 

分析spa

     注意,每個節點就是一個對象,對象裏面有屬性,一個id,一個pid,pid就是當前節點的父節點,這樣才能構成上面的樹形。對象

 

方法一:blog

  解決問題的思路就是,遞歸循環判斷3個連續的節點,就好了。經過遞歸判斷當前選中的節點的爺父,3個節點,若是子節點、爺節點勾選上了,父節點沒有勾選上,證實斷層。遞歸

 

代碼實現get

checkNode : function(curGid, selectRowids,allData) {
    var that=this;
    var pid = "";
    for (var i = 0; i < allData.length; i++) {
        if (allData[i].gid == curGid) { // allData是這個樹的全部節點對象集合
    	    pid = allData[i].pgid;
    	    break;
    	}
    }
    if (pid=='#'||pid == undefined) {
         return true;
    } else {
    	 var ppid = "";
    	 for (var i = 0; i < allData.length; i++) {
    	     if (allData[i].gid == pid) {
    	         ppid = allData[i].pgid;
    	         break;
    	     }
    	 }
    	 // 若是當前子節點的上級節點沒有勾選,而且當前節點的上上級節點勾選了,說明斷層了。
    	 if (selectRowids.indexOf(pid) == -1 && selectRowids.indexOf(ppid)>-1) {
    	     return false;
    	  } else {
        // 這裏最叼,遞歸當前結點的上一個節點!!! return this.checkNode(pid, selectRowids, allData); } } }

 

方法二:io

  解決問題的思路就是,找出當前選中的節點集合,for循環每個選中的節點,而後經過遞歸方式,獲取當前選中節點的祖先集合,而後按照順序判斷最頂層祖先(一級),若是沒勾選,就無論它,而後接着判斷最頂層祖先的下級祖先(二級),若是有勾選,那麼判斷三級是否勾選,若是沒勾選上,證實斷層!這種方法更加的簡單暴力。不過期間複雜度比第一種方法要大。for循環

 

循環當前選中節點遞歸獲取全部上級節點算法

// node 表明當前循環的選中節點, upNodeList 表明當前節點的全部上級對象集合 allNode 表明這個樹的全部節點集合
var getUpNode = function (node, upNodeList,allNode) {
    var pNode = [];
    for (var i = 0; i < allNode.length; i++) {
        if (node.pid == allNode[i].id) {
            pNode = allNode[i]
            if (pNode.pid == "#" || pNode.pid == undefined) { //若是該節點就是一級節點
                return UpNodeList;
            }
            this.getUpNode(pNode, UpNodeList, this.allNode)
        }
    }
}

 

  

附件

附上個人頁面效果圖,增強一下印象

 

 

 --end--

相關文章
相關標籤/搜索