Как выбрать n-ую строку в таблице базы данных SQL? - PullRequest
353 голосов
/ 19 августа 2008

Мне интересно изучить некоторые (в идеале) независимые от базы данных способы выбора n -ой строки из таблицы базы данных. Также было бы интересно увидеть, как этого можно достичь, используя встроенную функциональность следующих баз данных:

  • SQL Server
  • MySQL
  • PostgreSQL
  • 1012 * SQLite *
  • Oracle

В настоящее время я делаю что-то вроде следующего в SQL Server 2005, но мне было бы интересно увидеть более независимые подходы других:

WITH Ordered AS (
SELECT ROW_NUMBER() OVER (ORDER BY OrderID) AS RowNumber, OrderID, OrderDate
FROM Orders)
SELECT *
FROM Ordered
WHERE RowNumber = 1000000

Кредит для вышеуказанного SQL: Веблог Firoz Ansari

Обновление: См. Ответ Троэльса Арвина относительно стандарта SQL. Troels, у вас есть ссылки, которые мы можем цитировать?

Ответы [ 29 ]

1 голос
/ 29 января 2015
SELECT
    top 1 *
FROM
    table_name
WHERE
    column_name IN (
        SELECT
            top N column_name
        FROM
            TABLE
        ORDER BY
            column_name
    )
ORDER BY
    column_name DESC

Я написал этот запрос для поиска N-й строки. Пример с этим запросом будет

SELECT
    top 1 *
FROM
    Employee
WHERE
    emp_id IN (
        SELECT
            top 7 emp_id
        FROM
            Employee
        ORDER BY
            emp_id
    )
ORDER BY
    emp_id DESC
1 голос
/ 19 августа 2008

В Sybase SQL Anywhere:

SELECT TOP 1 START AT n * from table ORDER BY whatever

Не забудьте ЗАКАЗАТЬ ПОТОМУ, иначе оно бессмысленно.

1 голос
/ 08 июня 2009
SELECT * FROM emp a
WHERE  n = (SELECT COUNT( _rowid)
              FROM emp b
             WHERE a. _rowid >= b. _rowid);
0 голосов
/ 20 июня 2018

Для сервера SQL следующий код вернет первую строку из таблицы.

declare @rowNumber int = 1;
    select TOP(@rowNumber) * from [dbo].[someTable];
EXCEPT
    select TOP(@rowNumber - 1) * from [dbo].[someTable];

Вы можете просмотреть значения примерно так:

WHILE @constVar > 0
BEGIN
    declare @rowNumber int = @consVar;
       select TOP(@rowNumber) * from [dbo].[someTable];
    EXCEPT
       select TOP(@rowNumber - 1) * from [dbo].[someTable];  

       SET @constVar = @constVar - 1;    
END;
0 голосов
/ 06 марта 2009

невероятно, что вы можете найти движок SQL, выполняющий этот ...

WITH sentence AS
(SELECT 
    stuff,
    row = ROW_NUMBER() OVER (ORDER BY Id)
FROM 
    SentenceType
    )
SELECT
    sen.stuff
FROM sentence sen
WHERE sen.row = (ABS(CHECKSUM(NEWID())) % 100) + 1
0 голосов
/ 17 июля 2017

Мне кажется, что для эффективности вам необходимо: 1) сгенерировать случайное число от 0 до единицы меньше, чем количество записей в базе данных, и 2) иметь возможность выбрать строку в этой позиции. К сожалению, разные базы данных имеют разные генераторы случайных чисел и разные способы выбора строки в позиции в наборе результатов - обычно вы указываете, сколько строк пропустить и сколько строк вы хотите, но это делается по-разному для разных баз данных. Вот что у меня работает в SQLite:

select * 
from Table 
limit abs(random()) % (select count(*) from Words), 1;

Это зависит от возможности использовать подзапрос в предложении limit (в SQLite это LIMIT , ) Выбор количества записей в таблице должен быть особенно эффективным, будучи частью метаданных базы данных, но это зависит от реализации базы данных. Кроме того, я не знаю, будет ли запрос фактически формировать набор результатов перед извлечением N-й записи, но я надеюсь, что в этом нет необходимости. Обратите внимание, что я не указываю предложение "order by". Возможно, было бы лучше «упорядочить» что-то вроде первичного ключа, который будет иметь индекс - получение N-й записи из индекса может быть быстрее, если база данных не может получить N-ую запись из самой базы данных без построения набора результатов. .

0 голосов
/ 02 июня 2017
select * from 
(select * from ordered order by order_id limit 100) x order by 
x.order_id desc limit 1;

Сначала выберите первые 100 строк, упорядочив их по возрастанию, а затем выберите последнюю строку, упорядочив по убыванию и ограничиваясь 1. Однако это очень дорогой оператор, поскольку он обращается к данным дважды.

0 голосов
/ 18 ноября 2016

Это то, как я бы делал это в DB2 SQL, я считаю, что RRN (относительный номер записи) хранится в таблице O / S;

SELECT * FROM (                        
   SELECT RRN(FOO) AS RRN, FOO.*
   FROM FOO                         
   ORDER BY RRN(FOO)) BAR             
 WHERE BAR.RRN = recordnumber
0 голосов
/ 01 октября 2015

Ничего особенного, никаких специальных функций, если вы используете Caché, как я ...

SELECT TOP 1 * FROM (
  SELECT TOP n * FROM <table>
  ORDER BY ID Desc
)
ORDER BY ID ASC

Учитывая, что у вас есть столбец идентификатора или столбец с датой, которому можно доверять.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...