using NCC.Dependency;
using System;
using System.Collections.Generic;
using System.Data;
using System.Linq;
using System.Reflection;
namespace NCC.Common.Util
{
///
/// 树形结构查询
/// 版 本:V1.20.15.0
/// 版 权:Wesley(https://www.NCCsoft.com)
/// 作 者:NCC开发平台组
///
[SuppressSniffer]
public static class QueryTreeUtil
{
///
/// 递归查询
///
///
/// 数据源
/// 查询条件
/// 主键
/// 上级
///
public static List TreeWhere(this List data, Predicate condition, Func idSelector, Func parentIdSelector)
{
List locateList = data.FindAll(condition);
List treeList = new List();
foreach (T entity in locateList)
{
treeList.Add(entity);
T currentNode = entity;
while (true)
{
string parentId = parentIdSelector(currentNode);
if (parentId == null)
break;
T upRecord = data.Find(a => idSelector(a) == parentId);
if (upRecord != null)
{
treeList.Add(upRecord);
currentNode = upRecord;
}
else
{
break;
}
}
}
return treeList.Distinct().ToList();
}
///
/// 递归查询
///
/// 数据源
/// 查询条件
/// 主键
/// 上级
///
public static DataTable TreeWhere(this DataTable data, string condition, string idSelector = "F_Id", string parentIdSelector = "F_ParentId")
{
DataRow[] drs = data.Select(condition);
DataTable treeTable = data.Clone();
foreach (DataRow dr in drs)
{
treeTable.ImportRow(dr);
string pId = dr[parentIdSelector].ToString();
while (true)
{
if (string.IsNullOrEmpty(pId) && pId == "0")
{
break;
}
DataRow[] pdrs = data.Select(idSelector + "='" + pId + "'");
if (pdrs.Length > 0)
{
treeTable.ImportRow(pdrs[0]);
pId = pdrs[0][parentIdSelector].ToString();
}
else
{
break;
}
}
}
return treeTable.DefaultView.ToTable(true);
}
///
/// 获取全部子节点
///
///
/// 数据源
/// 主键值
/// 主键
/// 上级
///
public static List TreeChildNode(this List data, string idValue, Func idSelector, Func parentIdSelector)
{
T thisEntity = data.Find(a => idSelector(a) == idValue);
foreach (PropertyInfo prop in thisEntity.GetType().GetProperties())
{
if (prop.Name == "ParentId" || prop.Name == "parentId")
{
prop.SetValue(thisEntity, "0", null);
break;
}
}
List treeList = new List();
treeList.Add(thisEntity);
ChildNode(data, idValue, idSelector, parentIdSelector, ref treeList);
return treeList;
}
#region Method
private static void ChildNode(this List data, string idValue, Func idSelector, Func parentIdSelector, ref List treeNodes)
{
List locateList = data.FindAll(a => parentIdSelector(a) == idValue);
if (locateList.Count > 0)
{
foreach (var item in locateList)
{
treeNodes.Add(item);
ChildNode(data, idSelector(item), idSelector, parentIdSelector, ref treeNodes);
}
}
}
#endregion
}
}