如何將列表數(shù)據(jù)轉(zhuǎn)化為樹型數(shù)據(jù)(二)

整體思路是將之前的對象,用List<Map<String, Object>>的方式包起來。
Map作為樹中的“節(jié)點”,其中有兩個key,data--數(shù)據(jù)本身,children--又一個List<Map<String, Object>>存放子“節(jié)點”。

總的來說分兩步。

第一步,將所有parent值為null的節(jié)點先放入最后返回的結(jié)果集中。
因為這些值沒有父節(jié)點,必定在樹型結(jié)果集的第一層,可以率先放入。
parent為空的節(jié)點.png

由于是制作成工具,所以取id和parentId的操作使用了反射。
DATA_FIELD其實就是字符串常量,也就是上方提到的map中的"data"字段。
map.put((String) getSelfIdMethod.invoke(node), true)這句話后面會做解釋。

第二步,遍歷所有列表數(shù)據(jù),并依次添加進現(xiàn)有的樹型結(jié)果集中。
遍歷剩余的列表數(shù)并加入樹型結(jié)果集中.png

同理,map.put((String)getSelfIdMethod.invoke(node), true)同理這句話后面作解釋。

添加進樹型結(jié)果集方法.png

在理解了這兩個核心步驟的前提下,現(xiàn)在來解釋關(guān)于上面方法中的map的問題。
上面的方法存在一個問題,就是列表結(jié)果集(list)本身數(shù)據(jù)的順序是數(shù)據(jù)庫查出來的,也就是不確定的。
如果按照順序方式只遍歷一遍來放入樹型結(jié)果集(resultList)中,那么有可能出現(xiàn)這樣一種情況。
如:節(jié)點B的父節(jié)點是A,同樣A也有父節(jié)點(有父節(jié)點的意思是不保證A在第一步中會被率先放入)。
但是在list中,B是在比A更靠前的位置,所以可能出現(xiàn),企圖將B加入樹型結(jié)果集的時候,A還不存在結(jié)果集里。
這次遍歷中,B便無法放入樹型結(jié)果集中,那么如果只遍歷一次,B就被遺漏了。

目前第一版解決方案就是圖中的方法,將已經(jīng)放入resultList的節(jié)點存入map。
并一直循環(huán)直到確保所有l(wèi)ist數(shù)據(jù)都放入resultList才停止。


map解決列表順序問題.png

現(xiàn)在我們能確保所有結(jié)果都能放入resultList了。但是如圖,我們面臨了新的問題。

數(shù)據(jù)庫的數(shù)據(jù)如果讓數(shù)據(jù)成環(huán),比如兩列數(shù)據(jù)互為parent這種情況。
while (map.size() < list.size())這句代碼會讓這個方法進入死循環(huán)。
下一節(jié)我們繼續(xù)解決這個問題。

最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請聯(lián)系作者
【社區(qū)內(nèi)容提示】社區(qū)部分內(nèi)容疑似由AI輔助生成,瀏覽時請結(jié)合常識與多方信息審慎甄別。
平臺聲明:文章內(nèi)容(如有圖片或視頻亦包括在內(nèi))由作者上傳并發(fā)布,文章內(nèi)容僅代表作者本人觀點,簡書系信息發(fā)布平臺,僅提供信息存儲服務。

友情鏈接更多精彩內(nèi)容