一个特定服务器上的“不明确的列名称”错误

时间:2010-05-07 12:02:46

标签: sql sql-server

此简单查询仅在一个数据库服务器上抛出“不明确的列名称TaskID”错误 。这是荒唐的。我们在不同的服务器和不同版本的SQL Server(2005/2008)上使用相同的数据库结构对此进行了测试,并且只有这个特定客户端的服务器才会抛出错误。我其实很沮丧。

SELECT Tasks.TaskID
FROM Tasks
INNER JOIN TaskHelpers ON TaskHelpers.TaskID = Tasks.TaskID
ORDER BY TaskID

是的,我知道我可以将Tasks.TaskID放入order by条款中,但由于某些原因我不能。{/ p>

6 个答案:

答案 0 :(得分:11)

如果在sql server 2000上运行查询,或者在兼容级别80或更低级别下运行查询,则会出现模糊的列名错误。在兼容级别为90或更高的sql server 2005/2008上,您的查询运行正常。

来自order by子句docs:

“在SQL Server 2005中,限定的列名和别名将解析为FROM子句中列出的列。如果order_by_expression未限定,则该值必须在SELECT语句中列出的所有列中唯一。”

答案 1 :(得分:8)

我妈妈说总是在查询中使用表名/别名来限定每一列,就像“始终包含INSERT中的所有列名”一样,并且就像“不要选择*”等。

除了让它变得更容易,因为它是自我记录源代码,如果您添加/更改列,则可以防止此错误。

检查您的兼容性级别,它们之间存在差异以及ORDER BY的工作原理!

通常,在兼容级别90及更高级别,SQL Server 2008的默认级别,没有表名/别名语句的ORDER BY会产生错误。

ALTER DATABASE Compatibility Level (Transact-SQL)请参阅部分:兼容级别80和级别90之间的差异

兼容级别设置为80

  

WHEN绑定列引用时   列的ORDER BY列表   在SELECT列表列中定义   歧义被忽略和列   前缀有时会被忽略。这个   可以导致结果集返回   意外的订单。

     

例如,带有的ORDER BY子句   单个两部分专栏   (。)使用的   作为SELECT中列的引用   列表被接受,但表别名   被忽略了。考虑以下   查询。

     

SELECT c1 = -c1 FROM t_table AS x   ORDER BY x.c1

     

执行时,列前缀为   在ORDER BY中被忽略。那种   操作不会发生   指定的源列(x.c1)为   预期;相反它发生在   派生的c1列,在中定义   查询。这个的执行计划   查询显示的值为   派生列首先计算和   然后对计算值进行排序。

兼容级别设置为90

  

列歧义引发错误。   列前缀(如果有),在中指定   绑定时不会忽略ORDER BY   到SELECT列表中定义的列。

     

请考虑以下问题。

     

SELECT c1 = -c1 FROM t_table AS x ORDER BY x.c1

     

执行时,列中的列前缀   ORDER BY子句不会被忽略。那种   操作发生在指定的源上   列(x.c1)如预期的那样。执行   此查询的计划显示排序   operator命令从t_table返回的行   然后是派生列的值   计算SELECT列表中定义的c1。

答案 2 :(得分:5)

您可以指定要排序的列的索引:

SELECT Tasks.TaskID
FROM Tasks
INNER JOIN TaskHelpers ON TaskHelpers.TaskID = Tasks.TaskID
order by 1

答案 3 :(得分:4)

哇。问题出在数据库兼容模式上。它被设置为“80”(sql 2000)。我已将其设置为90,现在查询工作正常。

有关兼容性级别的更多信息,请访问: http://msdn.microsoft.com/en-US/library/ms178653(SQL.90).aspx

答案 4 :(得分:1)

如果您尝试使用标识符怎么办?通过使用这些标识符,SQL Server知道要按哪个列排序。我从来没有以任何其他方式做过,从来没有遇到任何问题。我并不确切地说为什么sql需要这些标识符,显然他不知道在有不明确的列名的时候在哪里订购。尝试类似的事情;

SELECT t.TaskID
FROM Tasks t
INNER JOIN TaskHelpers th ON th.TaskID = t.TaskID
order by t.TaskID

编辑: 你不能的原因是什么? SQL抛出错误?

答案 5 :(得分:0)

你是什么意思不能?很明显,Tasks和TaskHelpers都有一个名为TaskID的列。您需要指明Order By中的列与哪个表相关联。