管理Entity Framework中的树结构
很多时候您需要在数据库中存储逻辑树的层次结构。这个问题有很多种实现方式,但最常见的是使用一个简单自关联的表,如下图所示

如果您映射此表与实体框架您将自动获得一个树状结构,您需将关系字段重命名,因为他们被命名为Employee和 Employee1,将他们重命名微Parent和Childs,这样使结构更清晰和易于理解。

现在我创建一个简单控制台应用程序,以递归的方式打印整棵树,代码如下:
public static void Print(Employee employee, Int32 level)
{
Console.WriteLine("{0}{1}", new String('-', level), employee.Name);
if (!employee.Childs.IsLoaded)
{
employee.Childs.Load();
} foreach (Employee child in employee.Childs)
{
Print(child, level + 1);
}
}
上面的Print方法以递归的方式打印整棵树的所有节点,接下来在main方法中调用该方法
public static void Main()
{
Console.WriteLine("Test");
using (TestEntities context = new TestEntities())
{
Employee root = context.Employee
.Where(e => e.Parent == null).First();
Print(root, 0);
}
}
实体框架在内存中构建整个树,输出结果如下:
Test
Alkampfer
-Guardian
--Clark
--John
-Joe
修改树的结构很简单,你只需要修改它的父节点就可以了。代码如下:
Employee Clark = context.Employee
.Where(e => e.Name == "Clark").First();
Employee Joe = context.Employee
.Where(e => e.Name == "Joe").First();
Clark.Parent = Joe;
删除节点时有点麻烦,因为删除包含子节点的节点时,EF会报告异常。所以最好的做法是建立一个方法遍历所有子节点。
public static void Visit(Employee employee, Action<Employee> visitAction)
{
visitAction(employee);
if (!employee.Childs.IsLoaded)
employee.Childs.Load();
foreach (Employee child in employee.Childs)
Visit(child, visitAction);
}
调用以上方法,遍历所有子节点完成删除。
using (TestEntities context = new TestEntities())
{
Employee root = context.Employee
.Where(e => e.Parent == null).First();
List<Employee> nodes = new List<Employee>();
Visit(root, nodes.Add);
nodes.ForEach(context.DeleteObject);
context.SaveChanges();
}
值得注意的是以上方法存在性能问题!
外语水平有限,大家可以直接看原文
原文:http://www.codewrecks.com/blog/index.php/2009/02/27/manage-trees-with-entity-framework/
管理Entity Framework中的树结构的更多相关文章
- Entity Framework 教程——Entity Framework中的实体类型
Entity Framework中的实体类型 : 在之前的章节中我们介绍过从已有的数据库中创建EDM,它包含数据库中每个表所对应的实体.在EF 5.0/6.0中,存在POCO 实体和动态代理实体两种. ...
- 关于Entity Framework中的Attached报错相关解决方案的总结
关于Entity Framework中的Attached报错的问题,我这里分为以下几种类型,每种类型我都给出相应的解决方案,希望能给大家带来一些的帮助,当然作为读者的您如果觉得有不同的意见或更好的方法 ...
- 关于Entity Framework中的Attached报错的完美解决方案终极版
之前发表过一篇文章题为<关于Entity Framework中的Attached报错的完美解决方案>,那篇文章确实能解决单个实体在进行更新.删除时Attached的报错,注意我这里说的单个 ...
- [转]在Entity Framework中使用LINQ语句分页
本文转自:http://diaosbook.com/Post/2012/9/21/linq-paging-in-entity-framework 我们知道,内存分页效率很低.并且,如果是WebForm ...
- 在Entity Framework中使用事务
继续为想使用Entity Framework的朋友在前面探路,分享的东西虽然技术含量不高,但都是经过实践检验的. 在Entity Framework中使用事务很简单,将操作放在TransactionS ...
- Entity Framework中的多个库操作批量提交、事务处理
在Entity Framework 中使用SaveChanges()是很频繁的,单次修改或删除数据后调用SaveChanges()返回影响记录数. 要使用批量修改或者批量删除数据,就需要SaveCha ...
- LinqToSql和ASP.NET Entity FrameWork 中使用事务
ASP.NET Entity FrameWork中: int flag = -1; if (this.URPmanagementEntities1.Connection.State != System ...
- Lazy<T>在Entity Framework中的性能优化实践
Lazy<T>在Entity Framework中的性能优化实践(附源码) 2013-10-27 18:12 by JustRun, 328 阅读, 4 评论, 收藏, 编辑 在使用EF的 ...
- Entity framework 中Where、First、Count等查询函数使用时要注意
在.Net开发中,Entity framework是微软ORM架构的最佳官方工具.我们可以使用Lambda表达式在Entity framework中DbSet<T>类上直接做查询(比如使用 ...
随机推荐
- html 添加flash标签 兼容firefox ie google
<object classid="clsid:d27cdb6e-ae6d-11cf-96b8-444553540000" width="550" heig ...
- HDU - 1142:A Walk Through the Forest (拓扑排序)
Jimmy experiences a lot of stress at work these days, especially since his accident made working dif ...
- 关于解决Springboot跨域请求的方法
前言 最近在项目中,由于前后分离,前台项目和后台项目部署的不在一台服务器,就产生了跨域的问题,特此记录下 正文 正常情况下,如果提示: 就可以判断是没有解决跨域的问题了. 在SSM中,我曾经这样解决过 ...
- mysql主从简单配置
第一步.配置主从,来自于博文 https://www.cnblogs.com/gl-developer/p/6170423.html 下面配置的步骤就直接复制了. 一.准备工作: 1.主从数据库版本最 ...
- vs2010 C++创建和使用动态链接库(dll)
一.用C++创建动态链接库项目: 1.打开Microsoft Visual Studio 2010,选择File->New->Project. 2.在NewProject中选择Inst ...
- gradle asciidoc 使用
备注: 次文档参考github 例子 1.环境准备 node npm (yarn) java KindleGen 备注: 具体的安装可以参考网上相关文档,KindleGen 下载地址:htt ...
- python从网络时间服务器获取并打印当前时间以及pip安装ntplib的一次体验
首先需要安装ntplib,科一通过pip安装. ubuntu下科一通过如下指令安装pip: $ sudo apt-get install python-pip 使用如下指令安装ntplib: $ su ...
- 从汇编的角度看待变量类型与sizeof的机制
1.动机:前段时间,一直有个疑问,就是编译器是从哪里知道数据的类型的,数据的类型是存在内存里面的么,因为自己调试编译器,发现内存中并没有多余的数据,后来在群上发问,才知道数据在编译成汇编的过程就知道数 ...
- 【备忘】windows环境下20行php代码搞定音频裁剪
先上图,由于最近的需求需要对语音文件进行处理,所以抽空研究了下php处理音/视频文件的处理,简单的demo处理,截取一个音频文件的前20秒,并保存新的媒体文件. 操作步骤: ①在此站点下载所需的辅助程 ...
- javascript基础-js函数
一.创建函数的方式 1)普通方式 function cal( num1, num2 ) { return num1+num2; } 2)使用变量初始化方式 var plus = function(nu ...