我有一个名为Roles
的模型:
public string CodeRole { get; set; }
public string Organisation { get; set; }
public string LabelRole { get; set; }
CodeRole
和LabelRole
包含唯一值,但Organisation
列包含大约12个类别。我想生成一个下拉列表,允许用户按Organisation
进行过滤。
因此,我想使用Entity Framework构建一个查询,该查询返回某种形式的list / array / collection我可以很容易地转换为List<SelectListItem>
,同时text
和value
相等到不同的Organisation
值。
我认为查询看起来像这样:
_context.Roles.GroupBy(r=> r.Organisation)
这会返回IGrouping<string,Roles>
个对象,但我不知道如何使用IGrouping
。
这样我就可以通过List<SelectListItem>
将ViewBag
传递到视图中的下拉列表。
编辑:基于Alexander Manekovskiy回复的最终解决方案
List<Roles> orgs = (List<DimRoles>)_context.Roles.GroupBy(f => f.Organisation).Select(r => r.FirstOrDefault()).ToList();
List<SelectListItem> items = new List<SelectListItem>();
foreach (DimRoles r in orgs)
items.Add(new SelectListItem { Text = r.Organisation, Value = r.Organisation });
答案 0 :(得分:2)
是的,你对GroupBy是对的,但是你需要只从组中选择第一个值:
_context.Roles.GroupBy(r=> r.Organisation).Select(r = r.First())
另一种可能的解决方案是使用Distinct扩展方法:
_context.Roles.Select(r=> r.Organisation).Distinct()
然后要获得List<SelectListItem>
,您可以使用选择:
_context.Roles.GroupBy(r=> r.Organisation).Select(r =>
{
var organization = r.First();
return new SelectListItem() { Name = organization , Value = organization }
}).ToList();
但就个人而言,我更倾向于使用另一种将IEnumerable<T>
转换为List<SelectListItem>
的扩展方法。这可能是这样的:
public static IEnumerable<SelectListItem> GetList<TEntity>(this IEnumerable<TEntity> collection, Expression<Func<TEntity, object>> keyExpression,
Expression<Func<TEntity, object>> valueExpression, object selectedValue = null)
{
var keyField = keyExpression.PropertyName();
var valueField = valueExpression.PropertyName();
return new SelectList(collection, keyField, valueField, selectedValue).ToList();
}
然后你可以像这样使用它:
_context.Roles.Distinct(new OrganizationEqualityComparer()).GetList(o => o.Organization, o => o.Organization);
但在这种情况下,您需要实现IEqualityComparer<Role>
,这非常简单:
class RoleOrganizationComparer : IEqualityComparer<Role>
{
public bool Equals(Role x, Role y)
{
if (Object.ReferenceEquals(x, y)) return true;
if (Object.ReferenceEquals(x, null) || Object.ReferenceEquals(y, null))
return false;
return x.Organization == y.Organization;
}
public int GetHashCode(Role role)
{
//Check whether the object is null
if (Object.ReferenceEquals(role, null)) return 0;
//Get hash code for the Name field if it is not null.
return role.Organization == null ? 0 : role.Organization.GetHashCode();
}
}