Seb*_*ico 5 c# entity-framework
我正面临异常ObjectContext实例已被释放,并且即使在使用Include方法之后也不能再用于需要连接的操作.
这里检索实体的函数:
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;
Run Code Online (Sandbox Code Playgroud)
这里使用的功能:
// 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);
Run Code Online (Sandbox Code Playgroud)
我知道使用正在关闭连接.我以为ToList()会在关闭之前实例化对象列表和include中的相关对象.
有人能指出我做错了吗?对不起,我的问题不明确.我明白包含在使用的括号内抛出异常的行正在工作,但我不明白为什么包含不起作用?
谢谢!
您的问题有三种解决方案。这些来自此处的链接,是链接到相关实体的三种方法。第一个解决方案是您一直在使用的延迟加载解决方案。只需将您的代码修改为此即可。它抛出异常的原因是因为延迟加载仅在您需要时才会发生。当您需要仅在少数实体上加载相关实体时,这是一个很好的解决方案。
// 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);
}
Run Code Online (Sandbox Code Playgroud)
第二种解决方案是使用急切加载(如@DavidG建议)。因为您只加载找到的第一个实体的相关实体,所以我不建议您在您的案例中使用它,因为它将加载所有 oQuantity 实体的 EquipmentSection 实体。在您的SelectByFormula方法中,使用相关链接中所示的 Include 语句,它将在第一次调用时加载它(它不会重复对数据库的访问,但会立即提取更多数据)。
第三种解决方案是避免依赖Lazy Loading,也是一个不错的方法。这是显式加载技术,需要您指定要EquipmentSection在指定实体上加载相关实体。
我希望这些解释对您有所帮助。
另外,您可能需要考虑在您的方法上返回 IQueryable SelectByFormula。这样,如果您必须过滤请求,就像使用First()仅获取第一次出现的方法一样,您就不会只提取一个实例的所有内容。