2010-10-08 11 views
13

MySQL udostępnia funkcję łańcuchową o nazwie FIELD(), która przyjmuje zmienną liczbę argumentów. Wartością zwracaną jest lokalizacja pierwszego argumentu na liście pozostałych. Innymi słowy:Co to jest funkcja serwera MS SQL Server podobna do funkcji FIELD() MySQL?

FIELD('d', 'a', 'b', 'c', 'd', 'e', 'f') 

powróci 4, ponieważ "d" jest czwartym argumentem po pierwszym.

Ta funkcja umożliwia sortowanie wyników zapytania na podstawie bardzo szczegółowej kolejności. W przypadku mojej obecnej aplikacji są cztery statusy, które muszę zarządzać: aktywne, zatwierdzone, odrzucone i przesłane. Jeśli jednak po prostu zamawiam przez kolumnę statusu, uważam, że użyteczność wynikowej listy jest mniejsza, ponieważ odrzucone i aktywne elementy statusu są ważniejsze niż te przesłane i zatwierdzone.

W MySQL mogę to zrobić:

SELECT <stuff> FROM <table> WHERE <conditions> ORDER BY FIELD(status, 'rejected', 'active','submitted', 'approved') 

a wyniki zostaną uporządkowane tak, że odrzucone zostały pierwsze pozycje, a następnie aktywne, i tak dalej. Tak więc wyniki zostały uporządkowane w malejącym znaczeniu dla odwiedzających.

Mogę utworzyć osobną tabelę, która wylicza ten poziom ważności dla statusów, a następnie zamawiam zapytanie w porządku malejącym, ale pojawiły się one kilka razy od czasu przejścia na MS SQL Server, więc pomyślałem, że " d zapytać, czy mogę uniknąć dodatkowej tabeli i nieco bardziej złożonych zapytań za pomocą wbudowanej funkcji podobnej do FIELD MySQL().

Dziękuję
David Kees

Odpowiedz

19

Korzystając CASE expression (SQL Server 2005+):

ORDER BY CASE status 
      WHEN 'active' THEN 1 
      WHEN 'approved' THEN 2 
      WHEN 'rejected' THEN 3 
      WHEN 'submitted' THEN 4 
      ELSE 5 
     END 

można użyć tej składni dla bardziej złożonej oceny (w tym kombinacje, lub jeśli trzeba użyj LIKE)

ORDER BY CASE 
      WHEN status LIKE 'active' THEN 1 
      WHEN status LIKE 'approved' THEN 2 
      WHEN status LIKE 'rejected' THEN 3 
      WHEN status LIKE 'submitted' THEN 4 
      ELSE 5 
     END 
+0

niesamowite rzeczy! Dzięki. –

0

Polecam CTE (serwer SQL 2005+). Nie trzeba powtarzać kodów statusu ani tworzyć oddzielnej tabeli.

WITH cte(status, RN) AS ( -- CTE to create ordered list and define where clause 
     SELECT 'active', 1 
UNION SELECT 'approved', 2 
UNION SELECT 'rejected', 3 
UNION SELECT 'submitted', 4 
) 
SELECT <field1>, <field2> 
FROM <table> tbl 
INNER JOIN cte ON cte.status = tbl.status -- do the join 
ORDER BY cte.RN -- use the ordering defined in the cte 

Powodzenia

Jason

Powiązane problemy