C#使用二叉树算法设计一个无限分级的树表

时间:2021-10-15 20:05:48

效果图:

C#使用二叉树算法设计一个无限分级的树表

数据库:

C#使用二叉树算法设计一个无限分级的树表

操作树的示意图:

C#使用二叉树算法设计一个无限分级的树表

控制器代码:

using Dw.Business;
using Dw.Entity;
using Dw.Utilities;
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Web.Mvc;
using System.Diagnostics;
using System.Data; namespace Dw.Web.Areas.School.Controllers
{
public class SitesController : PublicController<Sites>
{
SitesBll sitesbll = new SitesBll();
SitesDetailsBll sitesdetailsbll = new SitesDetailsBll();
Sys_UserBll userbll = new Sys_UserBll();
private Sys_DataDictionaryBll Sys_datadictionarybll = new Sys_DataDictionaryBll();
public override ActionResult Form()
{
string KeyValue = Request["KeyValue"];
//添加时获取的Id值
string Id = Request["Id"];
string Name = Request["Name"]; Sites entity = new Sites();
string SMSV,ALSV,ParentName="";
if (string.IsNullOrEmpty(KeyValue))
{
SMSV = "";
ALSV = "";
entity = null;
}
else
{
entity = repositoryfactory.Repository().FindEntity(KeyValue);
SMSV = entity.ShowMode;
ALSV = entity.Accesslimit; var pent = repositoryfactory.Repository().FindEntity(entity.ParentId);
ParentName = pent.Name;
}
//显示模式和权限限制下拉菜单
List<Sys_DataDictionaryDetail> ShowModeList = Sys_datadictionarybll.GetDataDictionaryDetailListByCode("ShowMode");
List<Sys_DataDictionaryDetail> Accesslimit = Sys_datadictionarybll.GetDataDictionaryDetailListByCode("Accesslimit");
var sml=ShowModeList.Select(m => new SelectListItem { Text = m.FullName, Value = m.Code });
var al = Accesslimit.Select(m => new SelectListItem { Text = m.FullName, Value = m.Code });
ViewBag.ShowMode = new SelectList(sml, "Value", "Text", SMSV);
ViewBag.Accesslimit = new SelectList(al, "Value", "Text", ALSV);
//获取栏目的父栏目名称和对应的值
ViewBag.Parent = ParentName;
//添加栏目时获取父栏目名称和Id值
if (Id != ""&&Id!=null)
{
var ent = repositoryfactory.Repository().FindEntity(Id);
ViewBag.AddParent = Id + "," + ent.Name;
} if (ManageProvider.Provider.Current().Account == "System")
{
List<Sys_User> userList = userbll.GetList();
//将数据封装到 SelectList中,制定要生成下拉框选项的value和text属性
SelectList uList = new SelectList(userList, "UserId", "RealName");
ViewBag.uList = uList.AsEnumerable();
}
else {
var UserId = ManageProvider.Provider.Current().UserId;
Sys_User User = new Sys_User();
User = userbll.GetList().SingleOrDefault(a => a.UserId == UserId);
string CompanyId = User.CompanyId;
List<Sys_User> userList = userbll.GetList().Where(a => a.CompanyId == CompanyId).ToList();
//将数据封装到 SelectList中,制定要生成下拉框选项的value和text属性
SelectList uList = new SelectList(userList, "UserId", "RealName");
ViewBag.uList = uList.AsEnumerable();
} return View(entity);
} /// <summary>
/// 提交表单
/// </summary>
/// <param name="entity">实体对象</param>
/// <param name="KeyValue">主键值</param>
/// <returns></returns>
[HttpPost]
[ValidateInput(false)]
[LoginAuthorize]
public override ActionResult SubmitForm(Sites entity, string KeyValue)
{
try
{
int IsOk = ;
string Message = KeyValue == "" ? "新增成功。" : "编辑成功。";
if (!string.IsNullOrEmpty(KeyValue))
{
Sites Oldentity = repositoryfactory.Repository().FindEntity(KeyValue);//获取没更新之前实体对象
if (entity.AuditUserId != null)
{
Sys_User User = new Sys_User();
User = userbll.GetEntity(ManageProvider.Provider.Current().UserId);
string AuditUserName = User.RealName;
entity.AuditUserName = AuditUserName;
}
else { } entity.CompanyId= ManageProvider.Provider.Current().CompanyId;
entity.Modify(KeyValue);
IsOk = repositoryfactory.Repository().Update(entity);
if (entity.ParentId != Oldentity.ParentId)
{
sitesbll.UpLR();
}
WriteLog(IsOk, entity, Oldentity, KeyValue, Message);
}
else
{
if (ManageProvider.Provider.Current().Account == "System")
{ }
else { if (entity.AuditUserId != null)
{
Sys_User User = new Sys_User();
User = userbll.GetList().SingleOrDefault(a => a.UserId == entity.AuditUserId);
string AuditUserName = User.RealName;
entity.AuditUserName = AuditUserName;
}
else { } entity.CompanyId = ManageProvider.Provider.Current().CompanyId; }
entity.Create();
string strId = SysFactory.BaseHelper().GetSortCode<Sites>("Id").ToString();
entity.Id = int.Parse(strId);
IsOk = repositoryfactory.Repository().Insert(entity);
sitesbll.UpLR();
WriteLog(IsOk, entity, null, KeyValue, Message);
}
return Json(new { Success = true, Code = IsOk.ToString(), Message = Message });
}
catch (Exception ex)
{
WriteLog(-, entity, null, KeyValue, "操作失败:" + ex.Message);
return Content(new JsonMessage { Success = false, Code = "-1", Message = "操作失败:" + ex.Message }.ToString());
}
} /// <summary>
/// 删除栏目数据
/// </summary>
/// <param name="KeyValue">主键值</param>
/// <returns></returns>
[HttpPost]
[ManagerPermission(PermissionMode.Enforce)]
public ActionResult DeleteClass(string KeyValue)
{
try
{
string Message = "删除失败。";
int IsOk = ;
var sitesdetailsitem = sitesdetailsbll.FindList().Where(a => a.SitesId== int.Parse(KeyValue)).ToList();
var sitesitem = sitesbll.FindList().Where(a => a.ParentId == int.Parse(KeyValue)).ToList();
if (sitesdetailsitem.Count == )
{
if (sitesitem.Count == )
{
sitesbll.DelRelated(int.Parse(KeyValue));
IsOk = repositoryfactory.Repository().Delete(KeyValue);
} else {
Message = "该栏目下含有子栏目,不能删除";
};
}
else {
Message = "该栏目下含有文章,不能删除";
}; ////批量父子栏目删除
//sitesbll.DelRelated(int.Parse(KeyValue));
//IsOk = repositoryfactory.Repository().Delete(KeyValue);
if (IsOk > )
{
Message = "删除成功。";
}
WriteLog(IsOk, KeyValue, Message);
return Content(new JsonMessage { Success = true, Code = IsOk.ToString(), Message = Message }.ToString());
}
catch (Exception ex)
{
WriteLog(-, KeyValue, "操作失败:" + ex.Message);
return Content(new JsonMessage { Success = false, Code = "-1", Message = "操作失败:" + ex.Message }.ToString());
}
} /// <summary>
/// 栏目分类列表(返回树JSON)
/// </summary>
/// <returns></returns>
public ActionResult TreeJson()
{
string CompanyId = ManageProvider.Provider.Current().CompanyId;
var list = repositoryfactory.Repository().FindList("ORDER BY SortCode ASC").Where(a=>a.CompanyId==CompanyId).ToList();
List<TreeJsonEntity> TreeList = new List<TreeJsonEntity>(); foreach (Sites item in list)
{
int DataDictionaryId = item.Id;
bool hasChildren = false;
List<Sites> childnode = list.FindAll(t => t.ParentId == DataDictionaryId);
if (childnode.Count > )
{
hasChildren = true;
}
TreeJsonEntity tree = new TreeJsonEntity();
tree.id = DataDictionaryId.ToString();
tree.text = item.Name;
tree.value = item.ParentId.ToString();
tree.Attribute = "IsTree";
//tree.AttributeValue = item.IsTree.ToString();
tree.isexpand = true;
tree.complete = true;
tree.hasChildren = hasChildren;
tree.parentId = item.ParentId.ToString();
TreeList.Add(tree);
}
return Content(TreeList.TreeToJson());
}
public ActionResult TreeGridListJson()
{
string CompanyId = ManageProvider.Provider.Current().CompanyId;
var ListData = sitesbll.GetTable(CompanyId);
var aa = ListData.ToString();
StringBuilder sb = new StringBuilder();
sb.Append("{ \"rows\": ");
sb.Append(ListData.ToJson());
sb.Append("}");
return Content(sb.ToString());
} /// <summary>
/// 上移栏目数据
/// </summary>
/// <param name="KeyValue">主键值</param>
/// <returns></returns>
[HttpPost]
[ManagerPermission(PermissionMode.Enforce)]
public ActionResult Up(string KeyValue)
{
try
{
string Message = "上移失败。";
int IsOk = ;
string CompanyId = ManageProvider.Provider.Current().CompanyId;
var site1= sitesbll.GetEntity(int.Parse(KeyValue));
var level = site1.Level;
var site2 = sitesbll.FindList().SingleOrDefault(a => a.Level == site1.Level && a.CompanyId==CompanyId && a.Rgt==site1.Lft-);
if(site2!=null)
{
int? count1 = site1.Rgt - site1.Lft + ;
int? count2 = site2.Rgt - site2.Lft + ;
var sitesitem1 = sitesbll.FindList().Where(a => a.Lft>=site1.Lft && a.Rgt<=site1.Rgt).ToList();
var sitesitem2 = sitesbll.FindList().Where(a => a.Lft >= site2.Lft && a.Rgt <= site2.Rgt).ToList();
foreach (var item in sitesitem1)
{
item.Lft = item.Lft - count2;
item.Rgt = item.Rgt - count2;
item.Code = item.Code - count2/;
IsOk = repositoryfactory.Repository().Update(item);
} foreach (var item in sitesitem2)
{
item.Lft = item.Lft + count1;
item.Rgt = item.Rgt + count1;
item.Code = item.Code + count1 / ;
IsOk = repositoryfactory.Repository().Update(item);
}
}
else {
Message = "该栏目已经是该等级的最上层栏目不能上移!";
}; if (IsOk > )
{
Message = "上移成功。";
}
WriteLog(IsOk, KeyValue, Message);
return Content(new JsonMessage { Success = true, Code = IsOk.ToString(), Message = Message }.ToString());
}
catch (Exception ex)
{
WriteLog(-, KeyValue, "操作失败:" + ex.Message);
return Content(new JsonMessage { Success = false, Code = "-1", Message = "操作失败:" + ex.Message }.ToString());
}
} /// <summary>
/// 下移栏目数据
/// </summary>
/// <param name="KeyValue">主键值</param>
/// <returns></returns>
[HttpPost]
[ManagerPermission(PermissionMode.Enforce)]
public ActionResult Down(string KeyValue)
{
try
{
string Message = "下移失败。";
int IsOk = ;
string CompanyId = ManageProvider.Provider.Current().CompanyId;
var site1 = sitesbll.GetEntity(int.Parse(KeyValue));
var level = site1.Level;
var site2 = sitesbll.FindList().SingleOrDefault(a => a.Level == site1.Level && a.CompanyId == CompanyId && a.Lft== site1.Rgt + );
if (site2 != null)
{
int? count1 = site1.Rgt - site1.Lft + ;
int? count2 = site2.Rgt - site2.Lft + ;
var sitesitem1 = sitesbll.FindList().Where(a => a.Lft >= site1.Lft && a.Rgt <= site1.Rgt).ToList();
var sitesitem2 = sitesbll.FindList().Where(a => a.Lft >= site2.Lft && a.Rgt <= site2.Rgt).ToList();
foreach (var item in sitesitem1)
{
item.Lft = item.Lft + count2;
item.Rgt = item.Rgt + count2;
item.Code = item.Code + count2 / ;
IsOk = repositoryfactory.Repository().Update(item);
}
foreach (var item in sitesitem2)
{
item.Lft = item.Lft - count1;
item.Rgt = item.Rgt - count1;
item.Code = item.Code - count1 / ;
IsOk = repositoryfactory.Repository().Update(item);
}
}
else {
Message = "该栏目已经是该等级的最下层栏目不能下移!";
}; if (IsOk > )
{
Message = "下移成功。";
}
WriteLog(IsOk, KeyValue, Message);
return Content(new JsonMessage { Success = true, Code = IsOk.ToString(), Message = Message }.ToString());
}
catch (Exception ex)
{
WriteLog(-, KeyValue, "操作失败:" + ex.Message);
return Content(new JsonMessage { Success = false, Code = "-1", Message = "操作失败:" + ex.Message }.ToString());
}
} }
}

逻辑层代码:

using Dw.Entity;
using Dw.Repository;
using Dw.Utilities;
using System.Collections.Generic;
using System.Data;
using System.Text;
using Dw.DataAccess;
using System.Data.Common; namespace Dw.Business
{
/// <summary>
/// 网站栏目管理
/// </summary>
public class SitesBll : RepositoryFactory<Sites>
{
public List<Sites> GetList()
{
StringBuilder WhereSql = new StringBuilder(); ////有问题暂时这块先不设置此处的权限数据范围
//if (!ManageProvider.Provider.Current().IsSystem)
//{
// WhereSql.Append(" And (Id In (Select ResourceId From Sys_DataScopePermission Where");
// WhereSql.Append(" ObjectId IN ('" + ManageProvider.Provider.Current().ObjectId.Replace(",", "','") + "') ");
// WhereSql.Append(" ) )");
//}
WhereSql.Append(" ORDER BY Code,SortCode ASC");
return Repository().FindList(WhereSql.ToString());
} //public DataTable GetTable(ref JqGridParam jqgridparam)
public DataTable GetTable(string CompanyId)
{
StringBuilder strSql = new StringBuilder();
strSql.Append(@"Select S.Id,
S.CompanyId,
S.Code,
S.Expanded,
S.ParentId,
S.Name,
S.[Level],
S.Lft,
S.Rgt,
S.KeyWords,
S.Url,
S.PictureUrl,
D.FullName AS ShowMode,
S.Style,
L.FullName AS Accesslimit,
S.IsNav,
S.IsBlank,
S.SortCode,
S.CopyId,
S.CreateDate,
S.CreateUserId,
S.CreateUserName,
S.ModifyUserId,
S.ModifyDate,
S.ModifyUserName,
S.AuditUserName
FROM Sites AS S
INNER JOIN
(SELECT DataDictionaryId, FullName, Code
FROM Sys_DataDictionaryDetail
WHERE (DataDictionaryId IN (SELECT DataDictionaryId FROM Sys_DataDictionary WHERE (Code = 'ShowMode')))
) AS D ON S.ShowMode = D.Code INNER JOIN
(SELECT DataDictionaryId, FullName, Code
FROM Sys_DataDictionaryDetail
WHERE (DataDictionaryId IN (SELECT DataDictionaryId FROM Sys_DataDictionary WHERE (Code = 'Accesslimit')))
) AS L ON S.Accesslimit = L.Code");
if (!string.IsNullOrEmpty(CompanyId))
{
strSql.Append(" And S.CompanyId ="+"'" + CompanyId + "" + "' ");
}
strSql.Append(" ORDER BY Code,SortCode ASC");
return DataFactory.Database().FindTableBySql(strSql.ToString());
//strSql.Append(@"SELECT * FROM Sites Where 1=1");
//return Repository().FindTablePageBySql(strSql.ToString(), null, ref jqgridparam);
}
/// <summary>
/// 获取指定ParentId的List
/// </summary>
/// <param name="ParentId"></param>
/// <returns></returns>
public List<Sites> GetList(int ParentId)
{
StringBuilder WhereSql = new StringBuilder();
//if (!ManageProvider.Provider.Current().IsSystem)
//{
// WhereSql.Append(" And (Id In (Select ResourceId From Sys_DataScopePermission Where");
// WhereSql.Append(" ObjectId IN ('" + ManageProvider.Provider.Current().ObjectId.Replace(",", "','") + "') ");
// WhereSql.Append(" ) )");
//}
WhereSql.Append(" And ParentId=" + ParentId + "");
WhereSql.Append(" ORDER BY Code,SortCode ASC");
return Repository().FindList(WhereSql.ToString());
} public List<Sites> FindList()
{
return Repository().FindList();
} public Sites GetEntity(int KeyValue)
{
return Repository().FindEntity(KeyValue);
}
#region 无限分级的递归Left和Right赋值操作
int index = , Level = -, i = ;
/// <summary>
/// 无限分级的递归Left和Right赋值操作
/// </summary>
/// <param name="ParentId"></param>
public void UpLR(int ParentId)
{
Level++;
List<Sites> listData = GetList(ParentId);
var sites = new Sites();
foreach (var entity in listData)
{
sites.Id = entity.Id;
sites.Lft = index;
sites.Level = Level;
sites.Code = i++;
index++;
UpLR(entity.Id);
sites.Rgt = index;
index++;
DataFactory.Database().Update(sites);
}
Level--;
}
#endregion #region 递归删除栏目和子栏目
public void DelRelated(int Id)
{
string delstr = "";
var plist = Repository().FindList("ParentId", Id);
foreach (var item in plist)
{
delstr += item.Id + ",";
DelRelated(item.Id);
}
Repository().Delete(delstr.Split(',')); //批量删除
}
#endregion }
}

C#使用二叉树算法设计一个无限分级的树表的更多相关文章

  1. 基于react实现无限分级菜单

    在开发CMS(内容管理系统)系统时,一般都会用到一个侧边栏或者顶部的二级或者三级菜单,当点击或者鼠标悬浮时,菜单能够随之展开或收起. 本文纯粹为了练习一下react,因此我会在react环境下实现这么 ...

  2. 转:打造DropDownList&comma;TreeView&comma;ListBox无限极分类目录树

    [csharp] view plaincopyprint? #region DropDownList无限递归显示层次关系 /// <summary> /// 创建无限分级下拉列表框 /// ...

  3. 设单链表中存放n个字符,试设计一个算法,使用栈推断该字符串是否中心对称

    转载请注明出处:http://blog.csdn.net/u012860063 问题:设单链表中存放n个字符.试设计一个算法,使用栈推断该字符串是否中心对称,如xyzzyx即为中心对称字符串. 代码例 ...

  4. 笔试题&amp&semi;amp&semi;面试题:设计一个复杂度为n的算法找到单向链表倒数第m个元素

    设计一个复杂度为n的算法找到单向链表倒数第m个元素.最后一个元素假定是倒数第0个. 提示:双指针查找 相对于双向链表来说,单向链表仅仅能从头到尾依次訪问链表的各个节点,所以假设要找链表的倒数第m个元素 ...

  5. python学习&colon;设计一个算法将缺失的数字找出来。

    算法题   已知整型数值 a[99], 包含的所有99个元素都是从1-100中随机取值,并且这99个数两两互不相等,也就是说从1到100这100个数字有99个在数值内,有一个缺失.请设计一个算法将缺失 ...

  6. 设子数组A&lbrack;0&colon;k&rsqb;和A&lbrack;k&plus;1&colon;N-1&rsqb;已排好序&lpar;0&leq;K&leq;N-1&rpar;。试设计一个合并这2个子数组为排好序的数组A&lbrack;0&colon;N-1&rsqb;的算法。

    设子数组A[0:k]和A[k+1:N-1]已排好序(0≤K≤N-1).试设计一个合并这2个子数组为排好序的数组A[0:N-1]的算法.要求算法在最坏情况下所用的计算时间为O(N),只用到O(1)的辅助 ...

  7. 给定一个数组,它的第 i 个元素是一支给定股票第 i 天的价格。 &Tab;如果你最多只允许完成一笔交易(即买入和卖出一支股票),设计一个算法来计算你所能获取的最大利润。

    给定一个数组,它的第 i 个元素是一支给定股票第 i 天的价格. 如果你最多只允许完成一笔交易(即买入和卖出一支股票),设计一个算法来计算你所能获取的最大利润. 注意你不能在买入股票前卖出股票. 示例 ...

  8. 在一个N个整数数组里面,有多个奇数和偶数,设计一个排序算法,令所有的奇数都在左边。

    //在一个N个整数数组里面,有多个奇数和偶数,设计一个排序算法,令所有的奇数都在左边. // 例如: 当输入a = {8,4,1,6,7,4,9,6,4}, // a = {1,7,9,8,4,6,4 ...

  9. 痞子衡嵌入式:RT-UFL - 一个适用全平台i&period;MXRT的超级下载算法设计

    大家好,我是痞子衡,是正经搞技术的痞子.今天给大家带来的是痞子衡的开源项目 RT-UFL. 痞子衡在近两年多的i.MXRT客户项目支持过程中,遇到的一个相当高频的问题就是制作i.MXRT下载算法.我们 ...

随机推荐

  1. SQL Server Database 维护计划创建完整的备份策略

    SQL Server的维护计划Maintenance Plan是一个非常实用的维护工具,可以完成大多数的数据库维护任务,通过对这些功能的封装,可以省去很多的代码编写时间.网络上完整介绍的不是很多,特此 ...

  2. markdown思维导图笔记

  3. 你应该知道的16个Linux服务器监控命令

    在不同的Linux发行版中,会有不同的GUI程序可以显示各种系统信息,比如SUSE Linux发行版中,就有非常棒的图形化的配置和管理工具YaST,KDE桌面环境里的KDE System Guard也 ...

  4. AOP举例子

    切面类TestAspect package com.spring.aop; /** * 切面 * */ public class TestAspect { public void doAfter(Jo ...

  5. jQuery&period;fn

    DIY一个jQuery 写了一个非常简单的 jQuery.fn.init 方法: jQuery.fn.init = function (selector, context, root) { if (! ...

  6. 高橋君とホテル &sol; Tak and Hotels

    高橋君とホテル / Tak and Hotels Time limit : 3sec / Stack limit : 256MB / Memory limit : 256MB Score : 700  ...

  7. mysql--构造数据、导入导出

    一.mysql造数据脚本     DELIMITER $$ DROP PROCEDURE IF EXISTS `test3`$$ CREATE     /*[DEFINER = { user | CU ...

  8. kubelet集群网络配置flannel(覆盖网络)

    kubernetes本身并不会对跨主机容器的网络进行设置,这需要额外的工具来实现.一些常用的开源工具主要包括flanne.OpenvSwitch.Weave.Calico等,这里面最常用的是flann ...

  9. &lbrack;Linux&rsqb; Linux的环境变量

    环境变量可以被系统,用户,shell以及其他程序来设定 登录系统后,系统读取/etc/profile 文件,设置环境变量,如果没有就跳过 检查主目录(/root)的.profile文件,推荐去这个文件 ...

  10. java常见错误总结

    1. 现象:将数组转为List后进行removeAll()操作,报java.lang.UnsupportedOperationException错误. 代码: /** * 获取标记ID * @retu ...