我正面临异常即使在使用Include方法之后,ObjectContext实例也已被处置并且不能再用于需要连接的操作。
这里是检索实体的函数:
public List<Entity.CapacityGrid> SelectByFormula(string strFormula, int iVersionId)
{
// declaration
List<Entity.CapacityGrid> oList;
// retrieve ingredients
oList = (from Grid in _Dc.CapacityGrid.Include("EquipmentSection")
join Header in _Dc.CapacityHeader
on Grid.HeaderId equals Header.HeaderId
where Header.Formula == strFormula
&& Header.VersionId == iVersionId
select Grid).ToList();
// return
return oList;
这里使用函数:
// retrieve ingredient quantity by equipement
using (Model.CapacityGrid oModel = new Model.CapacityGrid(Configuration.RemoteDatabase))
oQuantity = oModel.SelectByFormula(strFormulaName, iVersionId);
// code to throw the exception
var o = (oQuantity[0].EquipmentSection.TypeId);
我知道使用正在关闭连接。我以为ToList()会在关闭之前实例化对象列表和include中的相关对象。
有人能指出我做错了什么吗? 对不起,我的问题不明确。我明白包含在使用的括号内抛出异常的行是可行的,但我不知道为什么包含不起作用?
谢谢!
答案 0 :(得分:3)
尝试更改
// retrieve ingredient quantity by equipement
using (Model.CapacityGrid oModel = new Model.CapacityGrid(Configuration.RemoteDatabase))
{ // <-- **add these**
oQuantity = oModel.SelectByFormula(strFormulaName, iVersionId);
// code to throw the exception
var o = (oQuantity[0].EquipmentSection.TypeId);
} // <-- **add these**
参考:http://msdn.microsoft.com/en-us/library/yh598w02.aspx
没有{}
来使用,连接就在第一行之后。因为实体框架使用表达式树(这意味着请求在真正需要之前不会执行),所以您的查询发生在var o = (oQuantity[0].EquipmentSection.TypeId);
。
答案 1 :(得分:1)
您的问题有三种解决方案。这些来自此链接here,是链接到相关实体的三种方式。第一个解决方案是您一直在使用的延迟加载解决方案。只需将您的代码修改为此代码即可。抛出异常的原因是因为只有在需要时才会发生延迟加载。当您只需要在几个实体上加载相关实体时,这是一个很好的解决方案。
// retrieve ingredient quantity by equipement
using (Model.CapacityGrid oModel = new Model.CapacityGrid(Configuration.RemoteDatabase))
{
oQuantity = oModel.SelectByFormula(strFormulaName, iVersionId);
// Lazy-load occurs here, so it needs to have access to the
// context, hence why it is in the using statement.
var o = (oQuantity.First().EquipmentSection.TypeId);
}
第二种解决方案是使用预先加载(如@DavidG所建议的)。因为您只加载找到的第一个实体的相关实体,所以我不建议您在您的情况下使用它,因为它将加载所有oQuantity实体的EquipmentSection实体。在SelectByFormula
方法中,使用相关链接中显示的Include语句,它将在第一次调用时加载它(它不会复制对数据库的访问,但它会一次提取更多数据)。 / p>
第三个解决方案是避免依赖Lazy Loading,这可能是一个很好的方法。它是显式加载技术,它要求您指定要在指定实体上加载EquipmentSection
相关实体。
我希望这些解释可以帮到你。
另外,您可能需要考虑在SelectByFormula
方法上返回IQueryable。这样,如果您必须过滤请求,例如使用First()
方法来获取第一次出现,那么您不会仅为一个实例提取所有内容。