用一列排序Linq列表
本文关键字:排序 Linq 列表 一列 | 更新日期: 2023-09-27 18:05:57
我想这应该很简单,但我找不到怎么做。我有一个linq查询,它选择了一个int类型的列,我需要对它排序。
var values = (from p in context.Products
where p.LockedSince == null
select Convert.ToInt32(p.SearchColumn3)).Distinct();
values = values.OrderBy(x => x);
SearchColumn3是op类型的字符串,但它只包含整数。所以我认为,转换为Int32和排序肯定会给我一个很好的1,2,3排序的值列表。但相反,列表保持有序,就像它是字符串一样。
199 20 201
更新:我用c#代码和LinqPad做了一些测试。LinqPad生成以下SQL:
SELECT [t2].[value]
FROM (
SELECT DISTINCT [t1].[value]
FROM (
SELECT CONVERT(Int,[t0].[SearchColumn3]) AS [value], [t0].[LockedSince], [t0].[SearchColumn3]
FROM [Product] AS [t0]
) AS [t1]
WHERE ([t1].[LockedSince] IS NULL)
) AS [t2]
ORDER BY [t2].[value]
我的SQL分析器说我的c#代码生成了这段SQL:
SELECT DISTINCT a.[SearchColumn3] AS COL1
FROM [Product] a
WHERE a.[LockedSince] IS NULL
ORDER BY a.[SearchColumn3]
所以看起来c# Linq代码省略了Convert.ToInt32。有人能说点有用的吗?
[免责声明-我在Telerik工作]
你也可以用Telerik OpenAccess ORM来解决这个问题。以下是我对这种情况的建议。
var values = (from p in context.Products
where p.LockedSince == null
orderby "cast({0} as integer)".SQL<int>(p.SearchColumn3)
select "cast({0} as integer)".SQL<int>(p.SearchColumn3)).ToList().Distinct();
OpenAccess提供了SQL扩展方法,它使您能够向生成的SQL语句添加一些特定的SQL代码。我们已经开始着手改善这种行为。谢谢你指出这一点。
对
拉尔夫与我的其他问题相同的答案,事实证明,我正在使用的Linq提供程序,与Telerik OpenAccess ORM附带的Linq提供程序做的事情不同于标准的Linq to SQL提供程序!看看我在我的开头贴出的SQL !我完全没有预料到这样的事情,但我似乎Telerik OpenAccess的事情仍然需要很多改进。所以在开始使用之前一定要小心。它看起来不错,但是有一些严重的缺点。
我无法重复这个问题。但要确保在检查集合时枚举它。你如何检查结果?
values = values.OrderBy(x => x);
foreach (var v in values)
{
Console.WriteLine(v.ToString());
}
请记住,这不会改变数据库或其他任何地方记录的顺序—只会改变您可以从values
枚举中检索它们的顺序。
因为你的values
变量是Linq
表达式的结果,所以它没有真正的值,直到你调用一个方法,如ToList
, ToArray
,等
回到您的示例,OrderBy
方法中的变量x
将被视为p.SearchColumn3
,因此,它是一个字符串。
为了避免这种情况,你需要让p.SearchColumn3
在OrderBy
方法之前变成整数。您应该在代码中添加一个let
语句,如下所示:
var values = (from p in context.Products
where p.LockedSince == null
let val = Convert.ToInt32(p.SearchColumn3)
select val).Distinct();
values = values.OrderBy(x => x);
此外,您可以将order by语句与第一个语句组合,这将是好的