Paging avec Oracle

Je ne suis pas aussi familier d’Oracle que j’aimerais être. J’ai quelques 250k enregistrements, et je veux les afficher 100 par page. Actuellement, j’ai une procédure stockée qui récupère tous les quart de million d’enregistrements dans un jeu de données en utilisant un adaptateur de données, un dataset et la méthode dataadapter.Fill (dataset) sur les résultats de la procédure stockée. Si j’ai le “numéro de page” et le “nombre d’enregistrements par page” comme valeurs entières, je peux passer comme parameters, quelle serait la meilleure façon de récupérer cette section particulière. Disons que si je passe 10 sous forme de numéro de page et 120 sous forme de nombre de pages dans la déclaration sélective, cela me donnerait les années 1880 à 1200, ou quelque chose comme ça, mes calculs dans ma tête pourraient être désactivés.

Je le fais en .NET avec C #, je pense que ce n’est pas important, si je peux le faire correctement du côté sql, alors je devrais être cool.

Mise à jour: J’ai pu utiliser la suggestion de Brian et cela fonctionne très bien. Je voudrais travailler sur une optimisation, mais les pages apparaissent dans 4 à 5 secondes au lieu d’une minute, et mon contrôle de pagination a pu s’intégrer très bien avec mes nouvelles procédures stockées.

Quelque chose comme ça devrait marcher: du blog de Frans Bouma

SELECT * FROM ( SELECT a.*, rownum r__ FROM ( SELECT * FROM ORDERS WHERE CustomerID LIKE 'A%' ORDER BY OrderDate DESC, ShippingDate DESC ) a WHERE rownum < ((pageNumber * pageSize) + 1 ) ) WHERE r__ >= (((pageNumber-1) * pageSize) + 1) 

Demandez à Tom sur la pagination et des fonctions analytiques très, très utiles.

Ceci est un extrait de cette page:

 select * from ( select /*+ first_rows(25) */ object_id,object_name, row_number() over (order by object_id) rn from all_objects) where rn between :n and :m order by rn; 

Dans un souci d’exhaustivité, pour les personnes à la recherche d’une solution plus moderne, dans Oracle 12c, il existe de nouvelles fonctionnalités, notamment une meilleure pagination et une meilleure gestion.

Pagination

La pagination ressemble à ceci:

 SELECT * FROM user ORDER BY first_name OFFSET 5 ROWS FETCH NEXT 10 ROWS ONLY; 

Top N Records

Obtenir les meilleurs enregistrements ressemble à ceci:

 SELECT * FROM user ORDER BY first_name FETCH FIRST 5 ROWS ONLY 

Notez comment les deux exemples de requête ci-dessus ont des clauses ORDER BY . Les nouvelles commandes les respectent et sont exécutées sur les données sortingées.

Je n’ai pas trouvé de bonne page de référence Oracle pour FETCH ou OFFSET mais cette page offre une excellente vue d’ensemble de ces nouvelles fonctionnalités.

Je veux juste résumer les réponses et les commentaires. Il y a plusieurs façons de faire une pagination.

Avant oracle 12c, il n’y avait pas de fonctionnalité OFFSET / FETCH, alors jetez un œil au livre blanc comme suggéré par @jasonk. C’est l’article le plus complet que j’ai trouvé sur différentes méthodes avec une explication détaillée des avantages et des inconvénients. Il faudrait beaucoup de temps pour les copier-coller ici, donc je ne le ferai pas.

Il y a aussi un bon article des créateurs de jooq expliquant certaines mises en garde courantes avec oracle et d’autres bases de données. le blogpost de jooq

Bonne nouvelle, depuis Oracle 12c, nous avons une nouvelle fonctionnalité OFFSET / FETCH. OracleMagazine 12c nouvelles fonctionnalités . S’il vous plaît se référer à “Top-N Query and Pagination”

Vous pouvez vérifier votre version d’Oracle en émettant la déclaration suivante

 SELECT * FROM V$VERSION 

Essayez ce qui suit:

 SELECT * FROM (SELECT FIELDA, FIELDB, FIELDC, ROW_NUMBER() OVER (ORDER BY FIELDC) R FROM TABLE_NAME WHERE FIELDA = 10 ) WHERE R >= 10 AND R < = 15; 

via [tecnicume]