SQL Server SELECT LAST N Rows

c'est une question connue mais la meilleure solution que j'ai trouvée est quelque chose comme:

SELECT TOP N *
FROM MyTable
ORDER BY Id DESC

j'ai une table avec beaucoup de lignes. Ce n'est pas une possibilité d'utiliser cette requête, parce que ça prend beaucoup de temps. Alors comment puis-je faire pour sélectionner les N dernières lignes sans utiliser la commande by?

MODIFIER

question dupliquée de celle-ci

104
demandé sur Community 2010-11-16 14:39:14

15 réponses

vous pouvez le faire en utilisant le numéro de ligne par la fonctionnalité de PARTITION aussi. Un grand exemple peut être trouvé ici :

j'utilise la table Orders de la base de données Northwind... Maintenant, récupérons les 5 dernières commandes placées par L'employé 5:

SELECT ORDERID, CUSTOMERID, OrderDate
FROM
(
    SELECT ROW_NUMBER() OVER (PARTITION BY EmployeeID ORDER BY OrderDate DESC) AS OrderedDate,*
    FROM Orders
) as ordlist

WHERE ordlist.EmployeeID = 5
AND ordlist.OrderedDate <= 5
33
répondu JonVD 2016-04-05 15:05:06

vous pouvez faire SQL server pour sélectionner les dernières N lignes en utilisant ce SQL:

select * from tbl_name order by id desc limit N;
74
répondu Niru Mukund Shah 2017-10-23 18:31:50

j'ai testé le code de JonVD, mais j'ai trouvé qu'il était très lent, 6s.

ce code a pris 0s.

SELECT TOP(5) ORDERID, CUSTOMERID, OrderDate    
FROM Orders where EmployeeID=5    
Order By OrderDate DESC
40
répondu ABI 2017-10-23 18:34:47

si vous voulez sélectionner les derniers nombres de lignes d'une table.

syntaxe sera comme

 select * from table_name except select top 
 (numbers of rows - how many rows you want)* from table_name

ces déclarations fonctionnent mais de manière différente. merci les gars.

 select * from Products except select top (77-10) * from Products

de cette façon, vous pouvez obtenir les 10 dernières lignes mais l'ordre montrera la manière de descendre

select top 10 * from products
 order by productId desc 

 select * from products
 where productid in (select top 10 productID from products)
 order by productID desc

 select * from products where productID not in 
 (select top((select COUNT(*) from products ) -10 )productID from products)
13
répondu Prafulla Sutradhar 2013-04-25 05:52:59

est-ce que " Id " est indexé? Si non, c'est une chose importante à faire (je soupçonne que c'est déjà indexé).

aussi, devez-vous retourner toutes les colonnes? Vous pouvez être en mesure d'obtenir une amélioration substantielle de la vitesse si vous avez seulement réellement besoin d'un plus petit sous - ensemble de colonnes qui peuvent être entièrement couverts par l'index sur la colonne ID-par exemple, si vous avez un index non corrigé sur la colonne Id, sans autres champs inclus dans l'index, alors il devrait faire une recherche sur le index cluster pour obtenir effectivement le reste des colonnes de retour et qui pourrait être de faire beaucoup du coût de la requête. Si c'est un index CLUSTERED, ou un index non clustered qui inclut tous les autres champs que vous voulez retourner dans la requête, alors vous devriez être bien.

6
répondu AdaTheDev 2010-11-16 11:51:48

D'abord, vous obtenez le plus grand nombre de disques de

 Declare @TableRowsCount Int
 select @TableRowsCount= COUNT(*) from <Your_Table>

et ensuite:

in SQL Server 2012

SELECT *
FROM  <Your_Table> As L
ORDER BY L.<your Field>
OFFSET <@TableRowsCount-@N> ROWS
FETCH NEXT @N ROWS ONLY;

in SQL Server 2008

SELECT *
FROM 
(
SELECT ROW_NUMBER() OVER(ORDER BY ID) AS sequencenumber, *
FROM  <Your_Table>
    Order By <your Field>
) AS TempTable
WHERE sequencenumber > @TableRowsCount-@N 
5
répondu Ardalan Shahgholi 2017-01-01 08:35:01

de manière très générale et pour supporter SQL server voici

SELECT TOP(N) *
FROM tbl_name
ORDER BY tbl_id DESC

et pour la performance, il n'est pas mauvais (moins d'une seconde pour plus de 10.000 enregistrements sur la machine serveur)

5
répondu Hakam Fostok 2018-03-03 13:58:24

Voici quelque chose que vous pouvez essayer sans un order by mais je pense qu'il exige que chaque ligne est unique. N est le nombre de lignes que vous voulez, L est le nombre de lignes dans la table.

select * from tbl_name except select top L-N * from tbl_name

comme indiqué ci-dessus, les lignes qui sont retournées ne sont pas définies.

EDIT: c'est en fait chien lent. Aucune valeur vraiment.

4
répondu Dzamo Norton 2013-04-17 08:00:32
select * from (select top 6 * from vwTable order by Hours desc) T order by Hours
4
répondu fth 2013-06-21 15:06:37

cette requête renvoie les N dernières lignes dans le bon ordre, mais sa performance est médiocre""

select *
from (
    select top N *
    from TableName t
    order by t.[Id] desc
) as temp
order by temp.[Id]
2
répondu timberhill 2014-03-04 09:19:34

ce n'est peut-être pas tout à fait la bonne réponse à la question, mais ...

OFFSET clause

la clause OFFSET number vous permet de sauter un nombre de lignes et ensuite retourner les lignes.

que doc link est à Postgres; Je ne sais pas si cela s'applique à Sybase/MS SQL Server.

2
répondu Basil Bourque 2014-03-17 23:41:32
DECLARE @MYVAR  NVARCHAR(100)
DECLARE @step  int
SET @step = 0;


DECLARE MYTESTCURSOR CURSOR
DYNAMIC 
FOR
SELECT col FROM [dbo].[table]
OPEN MYTESTCURSOR
FETCH LAST FROM MYTESTCURSOR INTO @MYVAR
print @MYVAR;


WHILE @step < 10
BEGIN   
    FETCH PRIOR FROM MYTESTCURSOR INTO @MYVAR
        print @MYVAR;
        SET @step = @step + 1;
END   
CLOSE MYTESTCURSOR
DEALLOCATE MYTESTCURSOR
0
répondu Slava 2015-10-19 11:34:56

Une technique que j'utilise pour interroger le les PLUS RÉCENTES lignes dans les très grandes tables (+de 100 millions de dollars, ou 1+ milliards de lignes) est la limitation de la requête à la "lecture" d'un seul "N" pourcentage de ces DERNIÈRES LIGNES. Ce sont des applications du monde réel, par exemple je le fais pour des données météorologiques récentes non historiques, ou des recherches récentes de flux de nouvelles ou des données de localisation GPS récentes.

C'est un énorme amélioration de la performance si vous savez avec certitude que vos lignes sont dans le TOP 5% Le plus récent du tableau par exemple. Ainsi, même s'il y a des indices sur les tableaux, cela limite encore les possibilités à seulement 5% des lignes dans les tableaux qui ont 100+ millions ou 1+ milliards de lignes. C'est particulièrement le cas lorsque des données plus anciennes nécessiteront disque physique lit et non seulement logique en mémoire lit.

This est bien plus efficace que SELECT TOP | PERCENT / LIMIT car il ne sélectionne pas les lignes, mais limite simplement la partie des données à rechercher.

DECLARE @RowIdTableA BIGINT
DECLARE @RowIdTableB BIGINT
DECLARE @TopPercent FLOAT

-- Given that there is an Sequential Identity Column
-- Limit query to only rows in the most recent TOP 5% of rows
SET @TopPercent = .05
SELECT @RowIdTableA = (MAX(TableAId) - (MAX(TableAId) * @TopPercent)) FROM TableA
SELECT @RowIdTableB = (MAX(TableBId) - (MAX(TableBId) * @TopPercent)) FROM TableB

SELECT *
FROM TableA a
INNER JOIN TableB b ON a.KeyId = b.KeyId
WHERE a.Id > @RowIdTableA AND b.Id > @RowIdTableB AND
      a.SomeOtherCriteria = 'Whatever'
0
répondu CodeCowboyOrg 2017-10-07 04:12:35

pour afficher les 3 dernières lignes sans utiliser order by :

select * from Lms_Books_Details where Book_Code not in 
 (select top((select COUNT(*) from Lms_Books_Details ) -3 ) book_code from Lms_Books_Details) 
-1
répondu abhinay 2012-09-28 15:31:37

essayez la syntaxe EXCEPT .

Quelque chose comme ceci:

   SELECT * 
    FROM   clientDetails 
    EXCEPT 
    (SELECT TOP (numbers of rows - how many rows you want) * 
     FROM   clientDetails) 
-1
répondu mayur godhani 2013-07-31 11:28:53