2008-10-04 5 views
4

Je cherchais à trier les tables par une colonne désignée comme donnée, et d'après ce que j'ai trouvé, il n'y a pas de moyen facile de le faire. Le meilleur que j'ai trouvé est une instruction switch:Est-il possible de commander par une colonne donnée un paramètre de procédure stockée dans SQL Server?

SELECT Column1, Column2, Column3, Column4 
FROM Table 
ORDER BY CASE WHEN @OrderBY = 'Column1' THEN Column1 
       WHEN @OrderBY = 'Column2' THEN Column2 
       WHEN @OrderBY = 'Column3' THEN Column3 
       WHEN @OrderBY = 'Column4' THEN Column4 

Est-il possible de le faire sans avoir une déclaration CASE comme ça? Si la table devient plus grande et que plus de colonnes doivent être triées, cela peut devenir désordonné. La seule façon de le faire est de concaténer une grosse chaîne SQL, ce qui annule les avantages des procédures stockées et rend le SQL difficile à écrire et à maintenir.

+0

Dupe de http://stackoverflow.com/questions/149380/dynamic-sorting-within-sql-stored-procedures –

Répondre

4

vous avez deux choix:

  1. Comme vous l'avez mis en place au-dessus

  2. Ou générer sql dynamique et exécuter en utilisant sp_executesql

+1

Ne jamais générer du SQL dynamique à l'intérieur ou à l'extérieur d'une procédure stockée, vous perdrez des performances car l'optimisé ne peut pas mettre en cache les instructions – massimogentilini

+0

Ce n'est pas vrai. Mon collègue découvre que, dans certains cas, le code généré est en réalité plus rapide que l'utilisation de @variables dans la procédure stockée. Nous ne savons vraiment pas pourquoi, mais c'est vrai. MSSQL2000, base de données 80 Go, plus de 300 connexions, 10 à 100 instructions sql/s, procédures stockées complexes – DiGi

+1

Avec sp_executesql, SQL Server stocke le plan d'exécution pour votre instruction. Si vous appelez sp_executesql avec la même requête mais avec des paramètres différents, le plan d'exécution sera réutilisé. En utilisant "exec" à la place aucun plan n'est conservé, vous perdez des performances. –

1

je convertir généralement la procédure stockée à une fonction qui retourne une table (ce que vous pouvez sélectionner ... et ajouter l'ordre dynamique en colonnes dans le code d'application:

Select 
    * 
From 
    myTableFUnction() 
Order by 
    1, 2, 3, 6 <-- defined by application code in the SQL for the query 

Ron

+0

également , Les fonctions ne peuvent pas contenir certains opérateurs (non déterministes). –

1

La fonction RANK de SQL Server et Oracle peut améliorer les performances et rend le code un peu plus propre:

SQL:

DECLARE @column varchar(10) 

SET @column = 'D' 

SELECT * 
FROM Collection.Account AS A 
ORDER BY 
     CASE 
      WHEN @column = 'A' THEN (RANK() OVER(ORDER BY A.Code ASC)) 
      WHEN @column = 'D' THEN (RANK() OVER(ORDER BY A.Code DESC)) 
     END 
-2

Dans ce cas, à moins d'avoir un jeu de données extrêmement volumineux et de tirer parti de la puissance du serveur de base de données (client léger, machine client faible, etc.), il est préférable de trier dans le client.

+0

Pourquoi cela serait-il exactement le cas? – Philluminati

1

Vous écrivez déjà la syntaxe correcte:

SELECT Column1, Column2, Column3 
FROM SOME_TABLE 
ORDER BY 1,2,3 

l'essayer