使用Entity Framework功能删除记录与直接使用DELETE stmt

时间:2013-10-05 19:56:26

标签: c# entity-framework-4

我在两张桌子之间有很多关系。

其中一项功能包括删除导航表中的所有记录,然后重新填充。

我使用Entity Framework,首先删除相关记录,然后通过以下方式重新填充该集合:

foreach (var funcionario in listFuncionario)
{
    int fun_id = 0;
    if (!int.TryParse(funcionario.Trim(), out fun_id))
        continue;
    var fun = db.Funcionario.Find(fun_id);
    fun.Servicio.ToList().ForEach(s => db.Servicio.Remove(s));
    fun.Servicio.Clear();
    foreach (var servicio in listServicio)
        fun.Servicio.Add(db.Servicio.Find(servicio));
}
db.SaveChanges();

这些循环非常慢(特别是删除),但是,当我使用ExecuteSqlCommand直接发出DELETEINSERT语句时,循环很快。

我不喜欢直接发布SQL命令,因为实体框架和面向对象编程的本质已经丢失。您是否知道使用Entity Framework以更有效的方式做到这一点?

此致 海梅

1 个答案:

答案 0 :(得分:1)

对于listFuncionario中的每个ID,您执行单独的查询(db.Funcionario.Find)。您可以通过一次性获取所有Funcionario条记录来加快速度。您需要先解析ID并将其存储在List<int>中,假设为idList

var funs = db.Funcionario.Where(f => idList.Contains(f.Id));

但您可以通过同时加载Servicio个收藏集来进一步优化:

var funs = db.Funcionario
             .Include("Servicio") // Or .Include(f => f.Servicio)
             .Where(f => idList.Contains(f.fun_id));

现在你可以做到

foreach(var fun in funs.ToList())
{
    fun.Servicio.ForEach(s => db.Servicio.Remove(s);
}

您可以对要添加的Servicio个对象执行相同的一次性查找,因此最终的解决方案是:

var servicio = db.Servicio.Where(s => listServicio.Contains(s.Id)).ToList();

var funs = db.Funcionario
             .Include("Servicio") // Or .Include(f => f.Servicio)
             .Where(f => idList.Contains(f.Id));

foreach(var fun in funs.ToList())
{
    fun.Servicio.ForEach(s => db.Servicio.Remove(s);
    foreach(var serv in servicio)
    {
        fun.Servicio.Add(serv);
    }
}

我认为Clear的{​​{1}}不是必需的。