2016-10-28 19 views
1

我正在構建面向數據庫的Web應用程序的查詢,並遇到SELECT DISTINCT和ORDER BY的問題。我希望顯示的第一個項目由變量確定(顯示用戶先前選擇了哪個選項),然後將其餘部分正常排序。在將DISTINCT選項添加到select(需要消除重複項)之前,我的ORDER BY正常工作。被排序的列出現在我的SELECT中,所以我不確定它爲什麼不接受它。「如果指定SELECT DISTINCT,則ORDER BY項目必須出現在選擇列表中」

WITH COURSE2 AS 
    (
    SELECT DISTINCT(SUBSTRING(section_table.crs_cde, 1, 10)) AS CRSID, yr_cde, trm_Cde FROM section_table 
    ) 
    SELECT DISTINCT crs_cde, crs_title 
     FROM course_table 
     LEFT JOIN COURSE2 
     ON crs_cde = CRSID 
     WHERE yr_cde = #currentyear# 
     AND trm_cde = #currentterm# 
     ORDER BY <cfif isDefined("FORM.ndd")>(case crs_cde when '#FORM.ndd#' then 0 else 1 end),</cfif> crs_cde ASC 

欣賞任何和所有幫助:)

回答

4

進行排序的列將出現在我的SELECT

不太。僅使用CASE語句中的相同列中的一列不計算在內。 ORDER BY引用必須完全匹配SELECT列表。另一種方法是將CASE移入SELECT列表中,作爲新列。然後排序列別名

SELECT DISTINCT crs_cde 
      , crs_title 
      , CASE crs_cde WHEN 'some value' THEN 0 ELSE 1 END AS SortOrder 

    FROM ... 
    ORDER BY SortOrder, crs_cde 

夫婦的有關查詢的其他意見:

WHERE yr_cde = #currentyear# AND trm_cde = #currentterm#

  1. 這將導致查詢轉換進入INNER JOIN。如果您確實需要外連接,請將這些篩選器移入CTE語句。

  2. 確保將所有可變參數包含在cfqueryparam中。在查詢中使用原始變量會使數據庫面臨sql注入的風險。

  3. 爲了清晰和易讀,請考慮添加表別名並使用它們來爲聯接查詢中的所有列加上前綴。

  4. 範圍內的所有變量,即使用FORM.someField而不只是someField

全部放在一起,像這樣(未測試)

WITH COURSE2 AS 
(
    SELECT DISTINCT(SUBSTRING(crs_cde, 1, 10)) AS CRSID 
    FROM section_table 
    WHERE yr_cde = <cfqueryparam value="#FORM.currentYear#" cfsqltype="cf_sql_integer"> 
    AND trm_cde = <cfqueryparam value="#FORM.currentTerm#" cfsqltype="cf_sql_integer"> 
) 
SELECT DISTINCT ct.crs_cde 
     , ct.crs_title 
     <cfif structKeyExists(FORM, "ndd")> 
     , CASE ct.crs_cde 
       WHEN <cfqueryparam value="#FORM.ndd#" cfsqltype="cf_sql_varchar"> THEN 0 
       ELSE 1 
      END AS SortOrder 
     </cfif> 
FROM course_table ct LEFT JOIN COURSE2 c2 ON c2.CRSID = ct.crs_cde 
ORDER BY 
    <cfif structKeyExists(FORM, "ndd")>SortOrder,</cfif> 
    crs_cde ASC 
相關問題