怎么样永久添加树节点?

怎么样永久添加树节点?,第1张

To: wonder_d
至少在我现在的知识层面上,我认为
如果要想把节点加上,在下次打开的时候就出现,只能用静态的方法。
其实,可能我没有完全理解你的意思。但是
我认为无论你静态添加,还是动态添加,都是可以,
因为软件总有一个启动过程我指的是软件,不是在vs中的写的代码,如
果写在vs中,那么只能用静态了,因为vs的代码,要ctrl+f5才能运行,只有
运行了才能去Add()。
----------------------------------------------
无论你保存在文件中,还是保存的数据库中
动态添加时你总要打开文件或是数据库
所以在运行前肯定没有了,以上我指的都是在vs中的
代码,如果你做成了软件,那么无论你怎么添加都肯定会有
----------------------------------------------
其实有也是刚刚学习的vs,希望我们可以共同进步,我只是把我的
理解写了出来,共勉吧!

1 可以使用递归方法进行展示
2 因为树形结构是由节点和节点之间的关系构成的,没有节点id会影响到节点的标识和关系的确定,但是我们可以根据节点之间的父子关系和其他属性来重构一个树形结构
3 在重构树形结构的过程中,可以使用递归的方法来不断向下遍历子节点,同时将节点的属性信息存储下来,最终构建出完整的树形结构。
同时也可以参考一些其他工具和库,如d3js、echarts等,这些工具可以帮助我们更方便地展示树形结构。

1、getNodeByParam 方法可以找到指定的节点数据
2、selectNode 方法可以选中节点,如果是 checkbox 的勾选,那么请使用 checkNode 方法

2019年7月26日
前言:树是一种数据结构的组织方式,不同的数据组织方式在数据的增删改查方面性能上有差异。例如ArrayList增删慢,其时间复杂度O(n),修改查询快,时间复杂度为O(1);LinkedList正好与ArrayList相反;而红黑树在增删改查的时间复杂度均为O(log(n))。接下来,是我对树的简单总结和理解。
全文缺少配图,有时间补上

树:从直接前继和直接后继个数角度,可以这样定义, 0到1个直接前继,0到n个直接后继,其中n>=2。
节点 :树就是由有限节点组成的一个具有层次关系的集合,数据就存在这些节点中。
根节点 :最顶上的一个节点,没有父节点。
子节点 :两个相连节点的关系。
叶子节点 :某个节点下方没有任何分叉。
节点的高度 :从某个节点出发,到叶子节点为止,最长简单路径上边的条数,称为该节点高度。
节点的深度 :从根节点出发,到某节点边的条数,称为该节点的深度。

(1)树的左右高度查不能超过1;
(2)任何往下递归的左子树和右子树,必须符合第一条性质;
(3)没有任何节点的空树或只有根节点的树也是平衡二叉树。

(1)对于任意节点来说,它的左子树上所有节点的值都小于他,而他的右子树上所有节点都大于他。
遍历所有节点的常用方式有三种:前序遍历、中序遍历、后序遍历。
(1)在任何递归子树中,左节点一定在右节点之前遍历。
(2)前序、中序、后序,仅指根节点在遍历时的为止顺序。
前序遍历顺序:根节点、左节点、右节点;
中序遍历顺序:左节点、根节点、右节点;
后序遍历顺序:做节点、右节点、根节点;
二叉查找树由于数据不断增加或删除容易失衡,因此为了保持二叉树重要的平衡性,有很多算法实现,比如AVL树、红黑树等

AVL树是一种平衡二叉查找树,在增加或删除节点后通过树形旋转重新达到平衡。
右旋,以某个节点为中心,将它沉入当前右子节点的位置,而让当前的左子节点作为新树的根节点,也称为顺时针旋转。
左旋,以某个节点为中心,将它沉入当前左子节点的位置,而让当前右子节点作为新树的跟节点,也称为逆时针旋转。

与AVL树相比,红黑树并不追求所有递归子树的高度差不超过1,而是保证从根节点到叶子节点的最长路径不超过最短路径的2倍。
相比二叉查找树,有5个约束条件:
(1)节点只能是红色或黑色。
(2)根节点必须是黑色。
(3)所有NIL节点都是黑色的。NIL,即叶子节点下挂的两个虚节点。
(4)一条路径上不能出现相邻的两个红色节点。
(5)在任何递归子树内,根节点到叶子节点所有路径上包含相同数目的黑色节点。

总结即是“有红必有黑,红红不相连”,上述5个约束条件保证了:
(1)红黑树的新增、删除、查找的最坏时间复杂度均为O(logn);
(2)如果一个树的左子节点或者右子节点不存在,则均认定为黑色;
(3)红黑树的任何旋转在3次之内均可完成。(这个是怎么计算出来的???)

这里还需更加详细分析两者的区别
面对频繁的插入和删除,红黑树更为合适;
面对低频修改、大量查询,AVL树更合适。

叶子节点:没有孩子节点的节点也就是说,当我们明白了叶子节点的定义后,只需要遍历一遍二叉树,把符合这种条件(左孩子节点和右孩子节点都为NULL的节点)的节点统计出来就可以了。于是,实际上这个问题也就转化成了如何遍历二叉树?很显然,遍历二叉树是可以有多种方式的,如:前序遍历(递归/非递归)、中序遍历(递归/非递归)、后序遍历(递归/非递归)、层次遍历等等。下面我将给出使用递归前序遍历以及层次遍历两种思路实现的求解叶子节点的示例代码吧,仅供参考。其他几种实现方式思路类似,可自行尝试。示例代码如下:package cnzifangskytreequestions;import orgjunitTest;import cnzifangskyqueueLinkQueue;import cnzifangskytreeBinaryTreeNode;/ 求二叉树中叶子节点的个数 @author Administrator /public class Question2 {/ 通过递归前序遍历获取叶子节点个数 @param root @return /public int getNumberOfLeavesByPreOrder(BinaryTreeNode root){if(root == null){return 0;}else{if(rootgetLeft() == null && rootgetRight() == null){ //叶子节点return 1;}else{return getNumberOfLeavesByPreOrder(rootgetLeft()) + getNumberOfLeavesByPreOrder(rootgetRight());}}}/ 使用层次遍历获取二叉树叶子节点个数 @时间复杂度 O(n) @param root /public int getNumberOfLeavesByQueue(BinaryTreeNode root){int count = 0; //叶子节点总数LinkQueue queue = new LinkQueue();if(root != null){queueenQueue(root);}while (!queueisEmpty()) {BinaryTreeNode temp = (BinaryTreeNode) queuedeQueue();//叶子节点:左孩子节点和右孩子节点都为NULL的节点if(tempgetLeft() == null && tempgetRight() == null){count++;}else{if(tempgetLeft() != null){queueenQueue(tempgetLeft());}if(tempgetRight() != null){queueenQueue(tempgetRight());}}}return count;}/ 测试用例 /@Testpublic void testMethods(){/ 使用队列构造一个供测试使用的二叉树 1 2 3 4 5 6 7 8 9 /LinkQueue queue = new LinkQueue();BinaryTreeNode root = new BinaryTreeNode(1); //根节点queueenQueue(root);BinaryTreeNode temp = null;for(int i=2;i /public class LinkQueue{private SinglyNode frontNode; //队首节点private SinglyNode rearNode; //队尾节点public LinkQueue() {frontNode = null;rearNode = null;}/ 返回队列是否为空 @时间复杂度 O(1) @return /public boolean isEmpty(){return (frontNode == null);}/ 返回存储在队列的元素个数 @时间复杂度 O(n) @return /public int size(){int length = 0;SinglyNode currentNode = frontNode;while (currentNode != null) {length++;currentNode = currentNodegetNext();}return length;}/ 入队:在链表表尾插入数据 @时间复杂度 O(1) @param data /public void enQueue(K data){SinglyNode newNode = new SinglyNode(data);if(rearNode != null){rearNodesetNext(newNode);}rearNode = newNode;if(frontNode == null){frontNode = rearNode;}}/ 出队:删除表头节点 @时间复杂度 O(1) @return /public Object deQueue(){if(isEmpty()){throw new RuntimeException("Queue Empty!");}else{Object result = frontNodegetData();if(frontNode == rearNode){frontNode = null;rearNode = null;}else{frontNode = frontNodegetNext();}return result;}}}单链表节点SinglyNode的定义:package cnzifangskylinkedlist;/ 单链表的定义 @author zifangsky @param /public class SinglyNode {private K data; // 数据private SinglyNode next; // 该节点的下个节点public SinglyNode(K data) {thisdata = data;}public SinglyNode(K data, SinglyNode next) {thisdata = data;thisnext = next;}public K getData() {return data;}public void setData(K data) {thisdata = data;}public SinglyNode getNext() {return next;}public void setNext(SinglyNode next) {thisnext = next;}@Overridepublic String toString() {return "SinglyNode [data=" + data + "]";}}

使用 TreeView 控件
TreeView
TreeView 控件可以用来显示具有层次结构的数据,例如组织树、索引项、磁盘中的文件和目录等。
图 240 典型的 TreeView
可能的用途
创建用户可以 *** 作的组织树。
创建能够显示至少两层或更多层的数据库树。
设置 Node 对象属性
“树”由一些层叠的“节点”分支构成,每个节点通常包括图象(用 Image 属性设置)和标签(由 Text 属性设置)。节点的图象由与 TreeView 控件相关联的 ImageList 控件提供。关于与其它控件共同使用 ImageList 控件的更多信息,请参阅“使用 ImageList 控件”。
节点可被展开或折回,这取决于它是否有子节点,即从它出发的节点。在最上层是“根”节点,每个“根”节点可以具有任何数目的子节点。节点的总数没有限制(除非受到机器资源的限制)。图 241 显示了具有两个根节点的树。其中“Root 1”有三个子节点,“Child 3”自己又有一个子节点。“Root 2”有子节点,由“+”号指出,但没有展开。
图 241 根和子节点
树中的每个节点实际上是可编程的 Node 对象,它属于 Nodes 集合。同在其它集合中一样,集合的每个成员具有唯一的 Index 和 Key 属性,通过这些属性可以访问相应节点的其它属性。例如,下面的代码用特定节点的 Index (“7”) 设置其 Image 和 Text 属性:
tvwMyTreeNodes(7)Image = "closed"
tvwMyTreeNodes(7)Text = "IEEE"
然而,如果唯一的键被赋给了该节点,例如“7 ID”,那么上述代码可被改写如下:
tvwMyTreeNodes("7 ID")Image = "closed"
tvwMyTreeNodes("7 ID")Text = "IEEE"
节点间的关系和对关系节点的引用
每个节点可以是子节点,也可以是父节点,这取决于它与其它节点之间的关系。Node 对象具有一些属性,可以用来返回子节点或父节点的各种信息。例如,下面的代码用 Children 属性返回某个节点的子节点个数。
MsgBox tvwMyTreeNodes(10)Children
然而,另外一些属性与 Children 属性不同,它们不返回信息,但返回对其它节点对象的引用。例如,Parent 属性返回对特定节点(只要该节点不是根节点)的父节点的引用。利用该引用,可以调用适用于 Node 对象的任何方法或设置属性来管理其父节点。例如,下面的代码返回父节点的 Text 和 Index 属性:
MsgBox tvwMyTreeNodes(10)ParentText
MsgBox tvwMyTreeNodes(10)ParentIndex
提示 使用 Set 语句处理 Node 类型的对象,以管理对其它 Node 对象的引用。例如,下面的代码将 Node 对象变量设置为 Parent 属性返回的引用。然后用该对象变量返回相关节点的属性:
Dim tempNode As Node '声明对象变量。
'将对象变量设置为返回的引用。
Set tempNode = tvwMyTreeNodes(10)Parent
MsgBox tempNodeText '返回父节点的 Text。
MsgBox tempNodeIndex '返回父节点的 Index。
向 Nodes 集合中添加 Node 对象
要将 Node 添加到树中,可以用 Add 方法(Nodes 集合)。该方法包括两个参数,relative 和 relationship,它们确定节点被加到何处。第一个参数 relative 指定节点名称,第二个参数 relationship 指定新加入的节点与名为 relative 的节点之间的关系。
例如,下面的代码添加名为“11 node”的节点,并使其成为名为“7 node”的节点的子节点。固有常数 tvwChild 指出新节点是前一参数所指定的节点的子节点。第三个参数设置新节点的 Key 属性。
tvwMyTreeNodesAdd "7 node", tvwChild, "11 node"
其它可能的关系包括:
常数 值 描述
tvwLast 1 该 Node 被放在所有与 relative 节点同级的节点之后。
tvwNext 2 该 Node 放在名为 relative 的节点之后。
tvwPrevious 3 该 Node 放在名为 relative 的节点之前。
tvwChild 4 该 Node 成为名为 relative 节点的子节点。
例如,假设已存在三个节点,如果想将第四个节点放在第二个和第三个节点之间,则代码如下:
'假设第二个节点的 Key 值为“2 node”。
tvwMyTreeNodesAdd "2 node", tvwNext
Add 方法的其它参数是 key、text 和 image。用这些参数,可以在创建 Node 对象时,为其赋予 Key、Text 和 Image 属性。
详细信息 关于 Nodes 集合 Add 方法的更多信息,请在索引搜索中键入“Add 方法”并单击“Add 方法 (Nodes 集合)”,参阅“Add 方法”。
添加节点的第二个方法是:声明 Node 类型的对象变量,然后使用带 Add 方法的 Set 语句。该 Set 语句将该对象变量设置为新节点。然后就可以用该对象变量设置节点的属性,如下所示:
Dim nodX As Node
Set nodX = tvwMyTreeNodesAdd("10 node", tvwChild)
nodXKey = "11 node"
nodXText = "IEEE"
nodXImage = "closed"
提示 使用带 Add 的 Set 语句,可使代码可读性强、容易调试。然而,如果使用 Add 方法及其参数添加节点,代码速度更快。
Listview
ListView 控件可使用四种不同视图显示项目。通过此控件,可将项目组成带有或不带有列标头的列,并显示伴随的图标和文本。
语法
ListView
说明
可使用 ListView 控件将称作 ListItem 对象的列表条目组织成下列四种不同的视图之一:
大(标准)图标
小图标
列表
报表
View 属性决定在列表中控件使用何种视图显示项目。还可用 LabelWrap 属性控制列表中与项目关联的标签是否可换行显示。另外,还可管理列表中项目的排序方法和选定项目的外观。
ListView 控件包括 ListItem 和 ColumnHeader 对象。ListItem 对象定义 ListView 控件中项目的各种特性,诸如:
项目的简要描述。
由 ImageList 控件提供的与项目一起出现的图标。
附加的文本片段,称作子项目,它们与显示在报表视图中的 ListItem 对象关联。
可以使用 HideColumnHeaders 属性决定是否在 ListView 控件中显示列标头。列标头可以在设计时添加,也可以在运行时添加。设计时,使用 ListView“控件属性”对话框的“列首”选项卡添加列标头。运行时,使用 Add 方法添加 ColumnHeader 对象到 ColumnHeaders 集合中。
发行注意 ListView 控件是 Mscomctlocx 文件中一组 ActiveX 控件的一部分。若要在应用程序中使用 ListView 控件,则必须将 Mscomctlocx 文件添加到工程中。当发行应用程序时,请将 Mscomctlocx 文件安装到用户的 Microsoft Windows System 或 System32 目录下。关于如何将 ActiveX 控件添加到 Visual Basic 工程的详细信息,请参阅 Visual Basic《程序员指南》。


欢迎分享,转载请注明来源:内存溢出

原文地址: https://outofmemory.cn/yw/13218039.html

(0)
打赏 微信扫一扫 微信扫一扫 支付宝扫一扫 支付宝扫一扫
上一篇 2023-06-22
下一篇 2023-06-22

发表评论

登录后才能评论

评论列表(0条)

保存