子查询中的 Order By 的 SQL 错误
Posted
技术标签:
【中文标题】子查询中的 Order By 的 SQL 错误【英文标题】:SQL Error with Order By in Subquery 【发布时间】:2010-11-02 10:10:05 【问题描述】:我正在使用 SQL Server 2005。
我的查询是:
SELECT (
SELECT COUNT(1) FROM Seanslar WHERE MONTH(tarihi) = 4
GROUP BY refKlinik_id
ORDER BY refKlinik_id
) as dorduncuay
还有错误:
ORDER BY 子句在视图、内联函数、派生中无效 表、子查询和公用表表达式,除非 TOP 或 FOR 还指定了 XML。
如何在子查询中使用ORDER BY
?
【问题讨论】:
【参考方案1】:当你有一个 UNION 时,可能需要订购一个子查询:
您生成所有教师和学生的电话簿。
SELECT name, phone FROM teachers
UNION
SELECT name, phone FROM students
您想先显示所有教师,然后显示所有学生,都按顺序显示。所以你不能应用全局订单。
一种解决方案是包含一个强制第一次排序的键,然后对名称进行排序:
SELECT name, phone, 1 AS orderkey FROM teachers
UNION
SELECT name, phone, 2 AS orderkey FROM students
ORDER BY orderkey, name
我认为它比伪造的偏移子查询结果更清楚。
【讨论】:
【参考方案2】:对于像 OP 显示的简单计数,Order by 并不是严格需要的。如果他们正在使用子查询的结果,则可能是。我正在处理一个类似的问题,并在以下查询中遇到了同样的错误:
-- 我想要更新日期等于最大更新日期的成本表中的行:
SELECT * FROM #Costs Cost
INNER JOIN
(
SELECT Entityname, costtype, MAX(updatedtime) MaxUpdatedTime
FROM #HoldCosts cost
GROUP BY Entityname, costtype
ORDER BY Entityname, costtype -- *** This causes an error***
) CostsMax
ON Costs.Entityname = CostsMax.entityname
AND Costs.Costtype = CostsMax.Costtype
AND Costs.UpdatedTime = CostsMax.MaxUpdatedtime
ORDER BY Costs.Entityname, Costs.costtype
-- *** 要做到这一点,有几个选项:
-- 添加一个无关的 TOP 子句,这似乎有点 hack:
SELECT * FROM #Costs Cost
INNER JOIN
(
SELECT TOP 99.999999 PERCENT Entityname, costtype, MAX(updatedtime) MaxUpdatedTime
FROM #HoldCosts cost
GROUP BY Entityname, costtype
ORDER BY Entityname, costtype
) CostsMax
ON Costs.Entityname = CostsMax.entityname
AND Costs.Costtype = CostsMax.Costtype
AND Costs.UpdatedTime = CostsMax.MaxUpdatedtime
ORDER BY Costs.Entityname, Costs.costtype
-- **** 创建一个临时表来订购 maxCost
SELECT Entityname, costtype, MAX(updatedtime) MaxUpdatedTime
INTO #MaxCost
FROM #HoldCosts cost
GROUP BY Entityname, costtype
ORDER BY Entityname, costtype
SELECT * FROM #Costs Cost
INNER JOIN #MaxCost CostsMax
ON Costs.Entityname = CostsMax.entityname
AND Costs.Costtype = CostsMax.Costtype
AND Costs.UpdatedTime = CostsMax.MaxUpdatedtime
ORDER BY Costs.Entityname, costs.costtype
其他可能的解决方法可能是 CTE 或表变量。但是每种情况都需要您确定最适合您的方法。我倾向于首先查看临时表。对我来说,它是清晰而直接的。 YMMV。
【讨论】:
【参考方案3】:美好的一天
对于某些人来说,子查询中的顺序是有问题的。 如果您需要基于某些排序删除某些记录,则必须使用子查询中的 order by。 喜欢
delete from someTable Where ID in (select top(1) from sometable where condition order by insertionstamp desc)
这样您就可以删除最后一个插入表格的表格。 实际上有三种方法可以执行此删除操作。
但是,子查询中的order by可以在很多情况下使用。
对于在子查询中使用order by的删除方法链接如下
http://web.archive.org/web/20100212155407/http://blogs.msdn.com/sqlcat/archive/2009/05/21/fast-ordered-delete.aspx
我希望它有所帮助。谢谢大家
【讨论】:
【参考方案4】:我使用此代码获得第二名的薪水
我也遇到类似错误
ORDER BY 子句在视图、内联函数、派生表、子查询和公用表表达式中无效,除非还指定了 TOP 或 FOR XML。
我用来避免错误的 TOP 100
从 ( select tbl.Coloumn1 ,CONVERT(varchar, ROW_NUMBER() OVER (ORDER BY (SELECT 1))) AS Rowno from ( 从表 1 中选择 前 100 名 * 按 Coloumn1 desc) as tbl) 为 tbl where tbl.Rowno=2
【讨论】:
【参考方案5】:如果您使用的是 SQL Server 2012 或更高版本,现在很容易解决此问题。添加offset 0 rows
:
SELECT (
SELECT
COUNT(1) FROM Seanslar WHERE MONTH(tarihi) = 4
GROUP BY refKlinik_id
ORDER BY refKlinik_id OFFSET 0 ROWS
) as dorduncuay
【讨论】:
在过去 20 分钟内我一直在寻找的所有答案中,这是唯一一个解决了我的问题的答案。 我避免了这个答案,因为它看起来如此多余和毫无意义,肯定会有更好的方法让它发挥作用!......不是。就是这样,这就是你们所有人的答案。多么奇怪的功能。 我在另一个问题here的回答中添加了一个在 SQL Server 的 CTE(临时命名结果集)上使用 ORDER BY 的示例 偏移0行是什么动作?【参考方案6】:也许这个技巧会对某人有所帮助
SELECT
[id],
[code],
[created_at]
FROM
( SELECT
[id],
[code],
[created_at],
(ROW_NUMBER() OVER (
ORDER BY
created_at DESC)) AS Row
FROM
[Code_tbl]
WHERE
[created_at] BETWEEN '2009-11-17 00:00:01' AND '2010-11-17 23:59:59'
) Rows
WHERE
Row BETWEEN 10 AND 20;
此处按字段 created_at 排序的内部子查询(可以是您表中的任何一个)
【讨论】:
【参考方案7】:如果构建临时表,请将 ORDER BY 子句从临时表代码块内部移到外部。
不允许:
SELECT * FROM (
SELECT A FROM Y
ORDER BY Y.A
) X;
允许:
SELECT * FROM (
SELECT A FROM Y
) X
ORDER BY X.A;
【讨论】:
【参考方案8】:除了 order by 在您的查询中似乎没有意义之外...... 要在子选择中使用 order by,您需要使用 TOP 2147483647。
SELECT (
SELECT TOP 2147483647
COUNT(1) FROM Seanslar WHERE MONTH(tarihi) = 4
GROUP BY refKlinik_id
ORDER BY refKlinik_id
) as dorduncuay
我的理解是“TOP 100 PERCENT”不再保证从 SQL 2005 开始的订购:
在 SQL Server 2005 中,ORDER BY 使用视图定义中的子句 只是为了确定那些是 由 TOP 子句返回。命令 BY 子句不保证订购 查询视图时的结果, 除非 ORDER BY 在 查询本身。
见SQL Server 2005 breaking changes
希望这会有所帮助, 帕特里克
【讨论】:
TOP 100 PERCENT 不保证订购。谢谢 这解决了我的问题!【参考方案9】:对我来说,这个解决方案也很好用:
SELECT tbl.a, tbl.b
FROM (SELECT TOP (select count(1) FROM yourtable) a,b FROM yourtable order by a) tbl
【讨论】:
【参考方案10】:尝试将 order by 子句移到 sub select 之外并在 sub select 中添加 order by 字段
SELECT * FROM
(SELECT COUNT(1) ,refKlinik_id FROM Seanslar WHERE MONTH(tarihi) = 4 GROUP BY refKlinik_id)
as dorduncuay
ORDER BY refKlinik_id
【讨论】:
【参考方案11】:将 Top 命令添加到您的子查询...
SELECT
(
SELECT TOP 100 PERCENT
COUNT(1)
FROM
Seanslar
WHERE
MONTH(tarihi) = 4
GROUP BY
refKlinik_id
ORDER BY
refKlinik_id
) as dorduncuay
:)
【讨论】:
【参考方案12】:您拥有的子查询(嵌套视图)会返回一个数据集,然后您可以在调用查询中对其进行排序。对子查询本身进行排序不会(可靠)改变调用查询中结果的顺序。
至于您的 SQL 本身: a) 当您返回单个值时,我认为没有理由订购。 b) 无论如何,我认为子查询没有任何理由,因为您只返回一个值。
我猜这里还有更多信息,您可能想告诉我们以解决您遇到的问题。
【讨论】:
【参考方案13】:这是你得到的错误(强调我的):
ORDER BY 子句在 视图,内联函数,派生 表、子查询和公用表 表达式,除非 TOP 或 FOR XML 是 也指定了。
那么,如何避免错误呢?通过指定 TOP,我猜是一种可能性。
SELECT (
SELECT TOP 100 PERCENT
COUNT(1) FROM Seanslar WHERE MONTH(tarihi) = 4
GROUP BY refKlinik_id
ORDER BY refKlinik_id
) as dorduncuay
【讨论】:
这不是按顺序排列的,如果您指定 top 99.99999 Percent 它会按预期工作 @foz1284 您能否指出一些证实此声明的文档或参考资料? blogs.msdn.com/b/queryoptteam/archive/2006/03/24/560396.aspx 如此处解释的 TOP 100 Percent 没有顺序,因为它保证返回所有悬停在 SQL Server 评估前 99 的行时,它需要执行顺序以确保它返回正确的行。 据我了解,这种特性只影响没有聚集索引的表,所以在使用TOP 100 PERCENT
时不会遇到一般问题。不过谢谢你的提示,我不知道。
我刚刚快速重读了一遍,我看到了您所引用的内容,前几天我正在订购一个将 3 个表联合在一起的子查询,这对我来说是个问题(我m 不是 SQL 专家,但我猜结果应该没有聚集索引!)【参考方案14】:
在此示例中,排序不添加任何信息 - 集合的 COUNT 与它的顺序相同!
如果您选择的东西 确实 取决于顺序,您需要执行错误消息告诉您的事情之一 - 使用 TOP 或 FOR XML
【讨论】:
【参考方案15】:您不需要在子查询中进行排序。将其移出到主查询中,并在子查询中包含您要排序的列。
但是,您的查询只是返回一个计数,所以我看不到 order by。
【讨论】:
以上是关于子查询中的 Order By 的 SQL 错误的主要内容,如果未能解决你的问题,请参考以下文章
SQL Server 查询错误 -ORDER BY 子句在视图中无效