2013-08-29 61 views
3

我有两个型号,一个是设备类型,另一个是设备的问题得到解决外键值。这里的关系是一个(DeviceType)到很多(DeviceIssues)。下面是型号:使用实体框架代码首先

public class DeviceType : ModelBase 
{ 
    public string Manufacture { get; set; } 
    public DeviceTypes Type { get; set; } 
    public string Model { get; set; } 

    public virtual ICollection<DeviceIssue> Issues { get; set; } 
} 

public class DeviceIssue : ModelBase 
{ 
    public string Description { get; set; } 
    public decimal RepairCost { get; set; } 

    public int DeviceTypeId { get; set; } 
    public virtual DeviceType DeviceType { get; set; } 
} 

public abstract class ModelBase 
{ 
    public int Id { get; set; } 
    public Guid Guid { get; set; } 
    public DateTime FirstCreated { get; set; } 
    public string LastUpdateUser { get; set; } 
    public DateTime LastUpdateDt { get; set; } 
    public bool IsDeleted { get; set; } 
} 

我必须填入几个实体数据库,使用种子的方法,以及它们的外键都完好无损。但是,当我得到设备类型的列表时,我也没有得到每个设备的相关问题列表。我使用的是AutoMapper,但是,调试存储查询结果的变量也不会显示数据。下面是我使用,使调用的代码:

var result = new List<DeviceTypeDataContract>(); 
using (var context = new DSPEntities()) 
{ 
    var devices = context.DeviceTypes; 
    foreach (var device in devices) 
    { 
     //var issues = context.DeviceIssues.Where(i => i.DeviceTypeId == device.Id).ToList(); 

     var devi = Mapper.Map<DeviceType, DeviceTypeDataContract>(device); 
     result.Add(devi); 
    } 
} 

现在的规定,在调试时,检查变量deviceforeach(var device in devices),显示如下类似的结果每次:

device.Issues = null, 
device.manufacture = "Apple", 
device.Model = "iPhone 3S", 
device.Type = DeviceTypes.SmartPhone, 

如果您请注意我的代码中有一段注释掉的代码。这是因为评论它引发以下内部异常:

{"There is already an open DataReader associated with this Command which must be closed first."}

我不知道这与我的具体问题,或者不这样做,虽然。

我的问题是,如何取回从这些关系中的数据?

注:关系确实存在,因为外面的foreach语句,调用下面:

var issues = context.DeviceIssues.Where(i => i.DeviceTypeId == 1).ToList(); 

给出以下结果:

issues[6].Description = "Water Damage", 
issues[6].RepairCost = 0.00, 
issues[6].DeviceTypeId = 1, 
issues[6].DeviceType = [+]{Data.Model.DeviceType}, 
// The last property holds values similar to above. 
// Except now the list of issues is populated. 

注意上面的评论:“除了现在的问题列表已填充。“

+0

['virtual'被推断延迟加载(http://stackoverflow.com/问题/ 5597760 /什么效果灿的虚拟关键字具备的,在实体框架-4-1-POCO码-FI)。您可以在'DbContext'调整延迟加载或使用'.INCLUDE()'方法,当你做查询主对象(所以它抓住协会以及)。例如'context.DeviceTypes.Include(x => x。DeviceIssues)' –

回答

5

当你装饰与virtual协会你推断他们是lazy loaded。这意味着,主要采集(在这种情况下DeviceTypes)被加载但,直到您尝试访问它,Issues将不会与任何信息填充。

有多种方式来解决这个问题,但最简单的(也是最有效的)是当你需要使用Include方法将其加载的关联。例如

var devices = context.DeviceTypes.Include(x => x.Issues); 

这将加载原始集合(DeviceTypes)以及填充Issues每种类型。这通常是因为你只抓取您需要的信息在需要时获得工作完成你的单位的最佳途径。

如果你发现这是常见的,但是,你总能在你DbContext构造调整延迟加载:

public DSPEntities() 
{ 
    this.Configuration.LazyLoadingEnabled = false; 
} 
+0

使用此方法会产生以下错误:'无法解析符号'Include''是否存在使用此方法所需的程序集? – Oxymoron

+1

yes:System.Data.Entity; – Oxymoron

+0

我在一个WCF项目中使用它,并且在调用使用此代码的特定操作合同时,会发生以下错误:“接收到http://xx.xx.x.xx的HTTP响应时发生错误:8200 /服务/WCFClient.svc。这可能是由于服务端点绑定不使用HTTP协议。这也可能是由于HTTP请求上下文被服务器中止(可能是由于服务关闭)。查看服务器日志以获取更多详细信息。]' – Oxymoron