功能:删除树形结构的空节点;
算法:1、先用AllOverTreeView函数递归遍历树形结构,将空节点添加到DelNodeList中;
2、然后再循环删除DelNodeList的所有节点;
优点:速度很快,只要便利一次树形结构就可以将所有要删除的节点地址保存下来;
1 procedure TfrmMain.DelHoldNodeWhereNoObject; 2 var 3 i: Integer; 4 TreeNode: TTreeNode; 5 DelNodeList: TList; 6 //高性能遍历树形结构 7 function AllOverTreeView(node:TTreenode):TTreenode; 8 var 9 childnode: TTreeNode; 10 begin 11 while node<>nil do 12 begin 13 if node.HasChildren then 14 begin 15 node := node.getFirstChild; 16 AllOverTreeView(node); 17 node := node.Parent; 18 end; 19 20 if (Node.Data <> nil) and (PTreeNodeInfo(node.Data)^.Count = 0) 21 and PTreeNodeInfo(node.Data)^.HoldFlag then 22 begin 23 DelNodeList.Add(node); 24 end; 25 26 if node.getNextSibling <> nil then 27 node := node.getNextSibling 28 else 29 Exit; 30 end; 31 end; 32 begin 33 DelNodeList := TList.Create; 34 try 35 TreeNode:=FObjTreeView.Items.GetFirstNode; 36 AllOverTreeView(TreeNode); 37 if DelNodeList.Count > 0 then 38 begin 39 for i := DelNodeList.Count -1 downto 0 do 40 begin 41 TTreeNode(DelNodeList.Items[i]).Delete; 42 end; 43 end; 44 finally 45 DelNodeList.Free; 46 end; 47 end; 48 49 if node.getNextSibling <> nil then 50 node := node.getNextSibling 51 else 52 Exit; 53 end; 54 end;
当要删除的节点很多时(几百上千),利用树形结构本身的delete函数删除节点的话效率很慢,耗时很长。原因是每次执行
Items.Delete(TreeNode);时都要遍历一次树形结构找到该节点的地址。当要删除的节点太多时就会严重影响性能。
下面是代码
procedure TfrmMain.DelHoldNodeWhereNoObject; var i: Integer; TreeNode: TTreeNode; begin with FObjTreeView do begin Canvas.Lock; for i := Items.Count - 1 downto 0 do begin TreeNode := Items[i]; if not TreeNode.HasChildren then begin if (TreeNode.Data <> nil) then begin if PTreeNodeInfo(TreeNode.Data)^.HoldFlag then begin Items.Delete(TreeNode); end; end; end; end; Canvas.Unlock; end; end;
(此处代码说明,
FObjTreeView :TtreeView;
PTreeNodeInfo是属性节点保存的数据结构;)
)