J'ai une base de données Oracle peuplée avec des millions d'enregistrements. J'essaie d'écrire une requête SQL qui renvoie les premiers enregistrements triés «N» (Dites 100 enregistrements) à partir de la base de données en fonction de certaines conditions.
SELECT * FROM myTable Where SIZE > 2000 ORDER BY NAME DESC
Mes questions sont: p>
5 Réponses :
ajoutez ceci: à votre endroit où la clause. P> Cependant, cela ne fera pas ce que vous demandez. P> Si vous souhaitez choisir 100 lignes aléatoires, triez-les, puis retournez-les, vous devrez formuler une requête sans la commande d'abord, puis limitez-la à 100 rangées, puis sélectionnez-la et triez. P> < p> Ceci pourrait em> travailler, mais malheureusement, je n'ai pas de serveur Oracle disponible pour tester: p> mais notez la partie "aléatoire" , tu dis "Donnez-moi 100 rangées avec taille> 2000, je m'en fiche de ce qui 100". p> est-ce vraiment ce que vous voulez? p> et non, vous avez gagné Il s'agit d'un résultat aléatoire, dans le sens où il changera chaque fois que vous interrogez le serveur, mais vous êtes à la merci de la requête Optimizer. Si la charge de données et les statistiques d'index pour ce tableau changent au fil du temps, vous pouvez obtenir différentes données que sur la requête précédente. P> P>
Merci d'avoir répondu. Ma requête ne doit pas être au hasard 100. Je souhaite obtenir les 100 premiers enregistrements triés. Pour ex: si les enregistrements sont compris entre 1,5,8,2,14,3,6,7. Et si je veux 3 enregistrements, la réponse serait (1,2,3)
Ensuite, vous DO I> voulez-vous trier en premier et si le tri de votre million de lignes prend beaucoup de temps, cela ne vous aidera pas beaucoup. Tout ce que vous faites, c'est éviter de récupérer toutes les lignes sur le réseau, le tri reste à courir.
Cependant, Oracle est suffisamment intelligente pour conserver les 100 premiers résultats. Si la ligne suivante est à l'extérieur de ce 100, il s'en écarte. De cette façon, il n'a pas besoin de trier tout le temps. Ceci est O (n) au lieu de O (n log n)
Si votre but est de trouver 100 lignes aléatoires et de les trier ensuite, puis La solution de Lasse est correcte. Si, comme je pense que vous voulez que les 100 premières lignes soient triées par leur nom tout en supprimant les autres, vous construirez une requête comme celle-ci:
SELECT /*+ FIRST_ROWS*/* FROM myTable WHERE SIZE > 2000 ORDER BY NAME DESC
Ce montre comment choisir les lignes TOPN en fonction de votre version d'Oracle. < / p>
de Oracle 9i à partir du rang () et Les fonctions dense_rank () peuvent être utilisées pour déterminer les lignes supérieures n. Exemples: P>
Obtenez les 10 meilleurs employés basés sur leur salaire p>
Sélectionnez Ename, Sal de (Sélectionner Ename, Sal, rang () sur (commander par Sal Desc) sal_rank De EMP) où Sal_RANK <= 10; P>
Sélectionnez les employés qui font le top 10 Salaires P>
Sélectionnez Ename, Sal de (Sélectionner Ename, Sal, dense_rank () sur (commande Par Sal desc desc) sal_dense_rank De EMP) où sal_dense_rank <= 10; P> blockQuote>
La différence entre les deux est expliquée ici P >
Votre problème est que le tri est effectué chaque fois que la requête est exécutée. Vous pouvez éliminer l'opération de tri en utilisant un index - l'optimiseur peut utiliser un index pour éliminer une opération de tri - si la colonne triée n'est déclarée pas NULL. P>
(Si la colonne est nullable, il est toujours possible, soit par (a) ajouter un prédicat non nul à la requête, ou (b) ajouter un index basé sur la fonction et modifier la commande par clause en conséquence). p>
Juste pour référence, dans Oracle 12c, cette tâche peut être effectuée à l'aide de la clause Fetch code>. Vous pouvez voir ici pour des exemples et des liens de référence supplémentaires concernant cette affaire. P>