我有一个方法CreateTreeView()
我打电话来将一个扁平的自引用表转换为树视图,如下所示。
ID | DisplayName | ParentID |
--------|----------------|------------|
1 | Top Level | NULL |
2 | Sub Level | 1 |
3 | Sub Level 2 | 2 |
4 | Top Level 2 | NULL |
public static void CreateTreeView()
{
using(var Context = new MyDBContext())
{
foreach(Department dept in Context.Departments.Where(d => d.IsVisible == true)
{
// Create the tree recursively
}
}
}
结果
-- TopLevel
|---Sub Level
|--- Sub Level 2
-- TopLevel2
这非常有效,并输出了jsTree在前端获取的JSON字符串。
我挣扎的是,有时我需要从不同的表格创建树视图。在上面的例子中,我查询了Department表。但是,我想概括我的CreateTreeView()
方法接受实体框架查询的结果并基于此生成树。
使用旧的ADO.NET方法,我会将结果填入SqlDataReader
并传递给它并使用它。但是,由于我是实体框架的新手,我正在努力将结果传递给方法,因为我在技术上可以将任何查询结果传递给它,因此如何导出对象类型等
理想情况下,我想象这样的事情(结果中的属性名称作为参数传递给方法)
public static void CreateTreeView(var results, string DataValueField, string ParentIDField, string DataTextField){
foreach(**UnknownObject** Result in results)
{
// Create the tree recursively
}
}
我已尝试将方法中的结果参数定义为IQueryable
等,但正如我上面所述,我不知道我将要传递的实体的类型英寸
我已经考虑过为不同的实体类型创建方法重载,但我不确定这是否是我需要采用的方式?感觉就像是在复制代码,这让我感到难过......
我真的只是朝着正确的方向寻找一个指针,我昨晚花了几个小时寻找东西,但我想我一直没有很好的搜索。
答案 0 :(得分:1)
您必须使用一些泛型。一种方法可能是这样的:
public static void CreateTreeView<TEntity, TValue>(IEnumerable<TEntity> results, Func<TEntity, TValue> dataField, Func<TEntity, int> parentField, Func<TEntity, string> dataTextField) {
foreach (TEntity result in results) {
var value = dataField(result);
var text = dataTextField(result);
int parentId = parentField(result);
// build your tree rerursively
}
}
这里有一组结果和一些函数,它们分别为给定的实体类型返回值,文本和父ID。用法是:
using(var Context = new MyDBContext())
{
var tree = CreateTreeView(Context.Departments.Where(d => d.IsVisible == true), c => c.DataField, c => c.ParentID, c => c.TextField);
}
另一种方法可能是为您的实体定义一个接口:
interface ITreeEntity<T> {
T Value {get;}
string TextField {get;}
int ParentID {get;}
}
允许构建实现该接口的实体树。然后,您不需要传递函数来明确获取值。