我目前有一个多对一关系层次结构数据库tblProjects-> tblLines-> tblGroups-> tblStations等。还有一个Entity框架6模型。
这些实体框架类都实现了基类“tblBase”:
public abstract class TblBase : INotifyPropertyChanged
{
private int _id;
public int ID
{
get
{
return _id;
}
set
{
_id = value;
NotifyPropertyChanged();
}
}
private Nullable<int> _coid;
public Nullable<int> COID
{
get
{
NotifyPropertyChanged();
return _coid;
}
set
{
_coid = value;
NotifyPropertyChanged();
}
}
private string _name;
public string Name
{
get
{
return _name;
}
set
{
_name = value;
NotifyPropertyChanged();
}
}
我有一个树视图,允许我选择任何节点作为父类型,目前我有一个方法,允许我重新加载所有子实体。
我想看看如何将它变成通用的:
private async static Task<bool> RefreshLinesAsync(LocalUser ThisUser, ProjectEntities DBContext, object Entity)
{
List<object> NonExistingNodes = new List<object>();
var bContinue = false;
var PassedEntity = Entity as TblBase;
//Scan through all DB child entities and reload their DB values
foreach (var SubEntity in DBContext.tblLines.Where(x => x.ProjectID == PassedEntity.ID).ToList())
{
await DBContext.Entry(SubEntity).ReloadAsync().ContinueWith(x =>
{
if (!x.IsFaulted)
{
if ((SubEntity.COID.GetValueOrDefault() != 0) && (SubEntity.COID.GetValueOrDefault() != ThisUser.ID))
NotifyCOIDConflict(SubEntity, new CheckedOutArgs()
{
ConflictCOID = SubEntity.COID.GetValueOrDefault()
});
bContinue = true;
}
}, TaskScheduler.FromCurrentSynchronizationContext());
if (bContinue)
//Continue to child entities method
await RefreshGroupsAsync(ThisUser, DBContext, SubEntity);
}
return true;
}
private async static Task<bool> RefreshGroupsAsync(LocalUser ThisUser, ProjectEntities DBContext, object Entity)
{
List<object> NonExistingNodes = new List<object>();
var bContinue = false;
var PassedEntity = Entity as TblBase;
foreach (var SubEntity in DBContext.tblGroups.Where(x => x.LineID == PassedEntity.ID).ToList())
{
await DBContext.Entry(SubEntity).ReloadAsync().ContinueWith(x =>
{
if (!x.IsFaulted)
{
if ((SubEntity.COID.GetValueOrDefault() != 0) && (SubEntity.COID.GetValueOrDefault() != ThisUser.ID))
NotifyCOIDConflict(SubEntity, new CheckedOutArgs()
{
ConflictCOID = SubEntity.COID.GetValueOrDefault()
});
bContinue = true;
}
}, TaskScheduler.FromCurrentSynchronizationContext());
if (bContinue)
await RefreshStationsAsync(ThisUser,DBContext, SubEntity);
}
return true;
}
我能看到的唯一有用的方法是Set(),虽然它没有提供Where()方法,这是至关重要的,因为我不想检索整个表。
答案 0 :(得分:1)
您可以使您的功能通用。他们可能喜欢这个:
private async static Task<bool> RefreshLinesAsync<TEntity>(LocalUser ThisUser, ProjectEntities DBContext, TEntity Entity) where TEntity : TblBase
{
List<TEntity> NonExistingNodes = new List<TEntity>();
var bContinue = false;
var PassedEntity = Entity as TblBase;
foreach (var SubEntity in DBContext.Set<TEntity>().Where(x => (x as TblBase).ProjectID == PassedEntity.ID).ToList()) {
//Your other code here...
}
}
函数定义中的where子句,确保只能使用TblBase的子类调用此方法。
编辑:
我忘了提到你需要在foreach循环中将SubEntity转换为TblBase才能使用它...
编辑(回复评论):如果需要从实体中获取所有TblBase子类,如果将它们保存在单独的表中,则不能使您的函数如此通用:当您必须添加更多子类时,它将变得难以实现。
我建议您通过Table Per Hierarchy使用单个表(请参阅MSDN中的this文章)将TblBase从抽象类更改为具体类,然后您可以通过这种方式获取所有这些:
var allSubClassEntities = DBContext.Set<TblBase>();