2011-02-18 44 views
3

當我運行鍼對MSSQL 2000MS SQL:嵌套的選擇 - 神祕的「無效列名稱」錯誤

SELECT 
    DISTINCT(Email), 
    (SELECT TOP 1 ActivityID 
     FROM Activity aa, ActivityType tt 
     WHERE aa.ActivityTypeId = tt.ActivityTypeId 
      AND aa.ConsumerID = c.ConsumerID 
      AND tt.ActivityType = 'Something_OptIn') optin, 
    (SELECT TOP 1 ActivityID 
     FROM Activity aa, ActivityType tt 
     WHERE aa.ActivityTypeId = tt.ActivityTypeId 
      AND aa.ConsumerID = c.ConsumerID 
      AND tt.ActivityType = 'Something_OptOut') optout 
FROM 
    Activity a, 
    Consumer c, 
    ActivityType t 
WHERE 
    c.CountryID = '23' 
    AND t.ActivityType = 'Something_Create' 
    AND a.ActivityTypeId = t.ActivityTypeId 
    AND c.ConsumerID = a.ConsumerID 
    AND optin > 1 

我收到以下錯誤

Server: Msg 207, Level 16, State 3, Line 1 
Invalid column name 'optin'. 

爲什麼會發生這種情況下查詢?我看不出爲什麼它會失效。

回答

5

SQL Server不允許您在同一級別通過名稱引用別名。爲了解決這個問題,重複列定義:

WHERE 
    c.CountryID = '23' 
    AND t.ActivityType = 'Something_Create' 
    AND a.ActivityTypeId = t.ActivityTypeId 
    AND c.ConsumerID = a.ConsumerID 
    AND (SELECT TOP 1 ActivityID 
     FROM Activity aa, ActivityType tt 
     WHERE aa.ActivityTypeId = tt.ActivityTypeId 
      AND aa.ConsumerID = c.ConsumerID 
      AND tt.ActivityType = 'Something_OptIn' 
     ) > 1 

或者使用子查詢:

SELECT * 
FROM (
     SELECT 
      DISTINCT(Email), 
      (...) optin, 
      (...) optout 
     FROM 
      Activity a, 
      Consumer c, 
      ActivityType t 
     ) as SubqueryAlias 
WHERE 
    c.CountryID = '23' 
    AND t.ActivityType = 'Something_Create' 
    AND a.ActivityTypeId = t.ActivityTypeId 
    AND c.ConsumerID = a.ConsumerID 
    AND optin > 1 
+0

它只適用於一個嵌套的SELECT,但不適用於optin和optout。請參閱https://gist.github.com/71efc3aa5bff219e98d7。 – joar 2011-02-18 14:36:09

1

最後一行AND optin > 1是罪犯。

WHERE子句對SELECT列表中的列別名一無所知。

您應該在沒有違規條件的情況下對該SELECT進行子查詢,並將該條件應用於外部SELECT。

SELECT * 
FROM (
    SELECT 
    ... 
    WHERE ... /* everything except 'optin > 1' */ 
) anyAlias 
WHERE optin > 1