我想知道如何从视图中执行升序和降序查询。我目前的观点如下:
我知道我可以使用以下内容订购视图:
Dim retrieveOrders = context.PBBuilds.Where(Function(x) x.User = userLoggedIn.Id).OrderBy(Function(x) x.Id).ToList()
我希望通过动作链接传递列标题并升序或降序到方法? (每个标题附近的向上和向下箭头)。
OrderBy()不接受字符串....任何人都可以帮忙吗?谢谢
控制器:
' GET: Dashboard
<Authorize(Roles:="Admin, Employee, User")>
Function Index() As ActionResult
Dim context = New ApplicationDbContext()
Dim UserManager = New UserManager(Of ApplicationUser)(New UserStore(Of ApplicationUser)(context))
Dim userLoggedIn = UserManager.FindById(User.Identity.GetUserId())
Dim retrieveOrders = context.PBBuilds.Where(Function(x) x.User = userLoggedIn.Id).OrderBy(Function(x) x.Id).ToList()
Dim BuildsVM = retrieveOrders.[Select](Function(build) New DashboardBuilds() With {
.BuildNumber = build.Id,
.DateCreated = build.TimeAndDate,
.MyRef = build.CustRef,
.NetCost = build.TotalNet
}).ToList()
Dim today = DateTime.Today.Date
Dim tomorrow = DateTime.Today.Date.AddDays(1)
Dim todaysBuild = retrieveOrders.Where(Function(build) build.TimeAndDate >= today And build.TimeAndDate <= tomorrow).ToList().Count()
Dim monthlyBuild = retrieveOrders.Where(Function(build) build.TimeAndDate.Year = today.Year And build.TimeAndDate.Month = today.Month).ToList().Count()
Dim yearlyBuild = retrieveOrders.Where(Function(build) build.TimeAndDate.Year = today.Year).ToList().Count()
Dim total As Decimal = BuildsVM.Sum(Function(item) item.NetCost)
Dim count As Integer = retrieveOrders.Count
Dim Average As Decimal = 0.00
If count > 0 Then
Average = total / count
End If
Dim model = New GroupedDashBoardBuilds() With {
.BuildInfos = BuildsVM,
.TotalNet = Math.Round(total, 2),
.AverageNet = Math.Round(Average, 2),
.TotalUserBuild = count,
.TotalUserBuildToday = todaysBuild,
.TotalUserBuildMonth = monthlyBuild,
.TotalUserBuildYear = yearlyBuild
}
Return View(model)
End Function
答案 0 :(得分:1)
由于您将传递字段名称以及是否要按升序或降序进入控制器:
Function Index(strColumnName As String, bolAscending As Boolean) As ActionResult
您可以在Select Case中实现逻辑,如下所示:
Dim retrieveOrders As List(Of PBBuilds) = Nothing
Select Case strColumnName
Case "Build"
If bolAscending Then
retrieveOrders = context.PBBuilds.Where(Function(x) x.User = userLoggedIn.Id).OrderBy(Function(x) x.Id).ToList()
Else
retrieveOrders = context.PBBuilds.Where(Function(x) x.User = userLoggedIn.Id).OrderByDescending(Function(x) x.Id).ToList()
End If
Case "My Reference"
If bolAscending Then
retrieveOrders = context.PBBuilds.Where(Function(x) x.User = userLoggedIn.Id).OrderBy(Function(x) x.FieldRelatedToMyReference).ToList()
Else
retrieveOrders = context.PBBuilds.Where(Function(x) x.User = userLoggedIn.Id).OrderByDescending(Function(x) x.FieldRelatedToMyReference).ToList()
End If
'Implement for Other Cases
End Select
答案 1 :(得分:0)
如果您不关心数据库上运行的OrderBy
,您可以执行以下操作:
Dictionary<string, Func<User, object>> ColumnAccessorMap = new Dictionary<string, Func<User, object>>()
{
{ "Build", user => user.ID },
{ "My Reference", user => user.MyReferenceProperty }
}
// etc...
context.MyTable.ToList().OrderBy(ColumnAccessorMap[strColumnName]);
或在VB.NET中(手工转换,很久没有使用过VB)
Dim ColumnAccessorMap as new Dictionary(of String, Object) From {{ "Build", Function(u) u.ID }, { "My Reference", Function(u) u.MyRefProperty }}
'... etc
context.MyTable.ToList().OrderBy(ColumnAccessorMap(strColumnName))
基本上,将列映射到访问器函数,该函数告诉OrderBy
排序时要使用的属性。同样,如果没有.ToList
之前的调用,这将无法工作,这意味着排序发生在本地,而不是在SQL中。