问题描述
我现在页面上显示的树结构:0:董事长1:财务总监2:财务主管3:出纳员3:报销员4:......2:税务主管3:......1:人事总监2:人事主管3:招聘4:办事员1:销售总监1:......2:...我要实现的内容是把上面这个树结构转换下面这个内容,内容显示没有问题,但是序号怎么弄没有思路了,如下:序号职务1董事长1.1财务总监1.1.1财务主管1.1.1.1出纳员1.1.1.2报销员1.1.1.1.1...1.2人事总监1.2.1人事主管1.2.1.1招聘1.2.1.1.1办事员1.3销售总监1.4......我现在数据库的结构是:parentchild董事长财务总监董事长人事总监董事长销售总监财务总监财务主管财务总监税务主管财务主管出纳员财务主管报销员...上面的这个序号(1,1.1,1.1.1,...)这个怎么实现呢?我现在使用的算法是递归,算法不能改了,结构不能改了,1级可以指定就是”董事长“,然后递归董事长下面的子级,就是这个序号怎么实现,请大神指教!!
解决方案
解决方案二:
从父集索引到自己,叠加即可
解决方案三:
已经是树了,还弄那么多点,有什么用啊非要这样,你直接把数据库里的序号改了比如原来是4,挂在1-2-3的下面,直接变成1.2.3.4,读取出来就也是这个号.
解决方案四:
既然有树了,那还不简单stringid="";while(node.Parent==null){id=node.Parent.id+""+id;node=node.Parent;}
解决方案五:
可以转成二叉树,然后用数组保存的方式保存,然后遍历数组就知道谁是root谁是child,遍历的时候就可以字符串加1.2.3这样。但是你说代码不能改结构不能改所以解决办法是。你做个字典吧map[董事长]="1"map[财务总监]="1.1"map[财务主管]="1.1.1"...最简单的办法是最有效的剩下的你应该明白了吧.
解决方案六:
我这个树不是固定的,上面只是我举的一个例子,实际上数据是变换的!
解决方案七:
stringid="";while(node.Parent==null){id=node.Parent.id+""+id;node=node.Parent;}
我现在数据库结构是改不了的,公司的项目,Parent.id,没有.id这个属性!
解决方案八:
要实现递归,对象上必须要绑定父节点的id,sostaticvoidMain(string[]args){List<Node>nodeList=CreateTestNodeList();DeepTestdt=newDeepTest();IDictionary<int,string>map=dt.CreatePrefix(nodeList);Deep(0,nodeList,map);}privatestaticvoidDeep(intparentId,List<Node>nodeList,IDictionary<int,string>map){foreach(NodenodeinnodeList.Where(item=>item.ParentID==parentId)){Console.WriteLine("{0}{1}",map[node.ID],node.ID);Deep(node.ID,nodeList,map);}}privatestaticList<Node>CreateTestNodeList(){List<Node>m_NodeList=newList<Node>(500);intindex=1;//rootm_NodeList.Add(newNode{ID=index});//一级子节点do{m_NodeList.Add(newNode{ID=++index,ParentID=1});}while(index<=10);//二级字节点foreach(Nodeiteminm_NodeList.Where(node=>node.ParentID==1).ToList()){do{m_NodeList.Add(newNode{ID=++index,ParentID=item.ID});}while(index%10!=0);}returnm_NodeList;}}classNode{publicintID{get;set;}publicintParentID{get;set;}}classDeepTest{///<summary>///生成节点的标题编号///</summary>///<paramname="nodeList">所有节点集合</param>///<returns>标题编号字典,key:节点id,value:编号</returns>publicIDictionary<int,string>CreatePrefix(List<Node>nodeList){intindex=1;IDictionary<int,string>map=newDictionary<int,string>(nodeList.Capacity);//遍历找到所有根节点foreach(NoderootinnodeList.Where(item=>item.ParentID==0)){stringprefix=index.ToString();map[root.ID]=prefix;Deep(root,nodeList,map);index++;}returnmap;}///<summary>///递归生成节点的标题编号///</summary>///<paramname="root">当前根节点</param>///<paramname="nodeList">所有节点集合</param>///<paramname="map">标题编号字典</param>privatevoidDeep(Noderoot,List<Node>nodeList,IDictionary<int,string>map){intid=root.ID,index=1;foreach(NodenodeinnodeList.Where(item=>item.ParentID==id)){stringprefix=map[id]+"."+index.ToString();map[node.ID]=prefix;index++;Deep(node,nodeList,map);}}}
解决方案九:
publicvoidCreateTree(stringlineNumber,intparentKey,List<object>datasource)
解决方案十:
引用6楼luluxiaoniu88的回复:
stringid="";while(node.Parent==null){id=node.Parent.id+""+id;node=node.Parent;}我现在数据库结构是改不了的,公司的项目,Parent.id,没有.id这个属性!
遍历一下树的所有结点,会不会?
解决方案十一:
使用递归实现系统导航示例//加载根节点开始递归调用填充TreeView树形控件protectedvoidPage_Load(objectsender,EventArgse){if(!IsPostBack){//获取数据连接语句,并创建数据库连接对象myConn=DBClass.GetConnection();CreateDataSet();InitTree(TreeView1.Nodes,"0");}}//选择数据库数据建立数据集对象返回数据publicDataSetCreateDataSet(){query="select*fromtbTree";myAdapter=newSqlDataAdapter(query,myConn);data=newDataSet();myAdapter.Fill(data,"tree");returndata;}//CodeGo.net///从DataSet中取数据建树//从根节点开始递归调用显示子树publicvoidInitTree(TreeNodeCollectionNds,stringparentId){TreeNodeNewNode;//data为存储建树数据信息的数据集//用父节点进行筛选数据集中信息DataRow[]rows=data.Tables[0].Select("parent_Id='"+parentId+"'");foreach(DataRowrowinrows){NewNode=newTreeNode(row["title"].ToString(),//设置父节点row["Files_Id"].ToString(),"images/1.gif",row["NavigateUrl"].ToString(),"");Nds.Add(NewNode);InitTree(NewNode.ChildNodes,row["Files_Id"].ToString());//添加子节点}}//点击节点跳转到指定页面protectedvoidTreeView1_SelectedNodeChanged1(objectsender,EventArgse){intnodeId=Convert.ToInt32(TreeView1.SelectedValue);//获取TreeView控件选择的值stringurl=DBClass.GetUrl(nodeId);//获取指定地址Response.Redirect(url.ToString());//转到指定页}//从数据库中获取控件中某个节点的关联地址publicstaticstringGetUrl(intfilesId){//获得url地址SqlConnectionmyConnection=GetConnection();SqlCommandmyCommand=newSqlCommand("GetUrl",myConnection);myCommand.CommandType=CommandType.StoredProcedure;//添加参数SqlParameterFilsesId=newSqlParameter("@FilesId",SqlDbType.Int,4);FilsesId.Value=filesId;myCommand.Parameters.Add(FilsesId);//添加参数SqlParameterUrl=newSqlParameter("@Url",SqlDbType.NVarChar,100);Url.Direction=ParameterDirection.Output;myCommand.Parameters.Add(Url);//执行存储过程myConnection.Open();myCommand.ExecuteNonQuery();stringurl=Url.Value.ToString();myCommand.Dispose();myConnection.Dispose();returnurl;}
解决方案十二:
引用6楼luluxiaoniu88的回复:
stringid="";while(node.Parent==null){id=node.Parent.id+""+id;node=node.Parent;}我现在数据库结构是改不了的,公司的项目,Parent.id,没有.id这个属性!
他给了你一个解题思路,没有ID这个属性的话,你就自己造一个呗。我的思路是这样的:在你生成树的时候,就可以得到你所需要的序号了。第一步,先生成根节点,也就是董事长的那个节点,设置那个节点的.tag=1,.Text=.tag+董事长。第二步,查找董事长的所有下属,将下属作为子节点加入到董事长节点下面,添加方式为.tag=父节点.tag+"."+这个下属的序号.Text=.tag+职务名称第三步,仿照第二步,查找第二步添加的下属的所有下属,然后加入树中。如果看到这里你已经明白了的话,就可以用递归来实现了。