web-dev-qa-db-ja.com

ORDER BYなしのROW_NUMBER

Redisに追加されたデータの量を追跡できるように、既存のクエリに行番号を追加する必要があります。クエリが失敗した場合、他のテーブルで更新されている行noから開始できます。

テーブルから1000行後にデータを取得するクエリ

SELECT * FROM (SELECT *, ROW_NUMBER() OVER (Order by (select 1)) as rn ) as X where rn > 1000

クエリは正常に機能しています。順序を使用せずに行を取得できる方法がある場合。

ここでselect 1とは何ですか?

クエリは最適化されていますか、他の方法で実行できます。より良い解決策を提供してください。

20
lucy

ORDER BY式で定数を指定することを心配する必要はありません。以下は、 ウィンドウ関数を使用したMicrosoft SQL Server 2012高性能T-SQLItzik Ben-Gan(Microsoftの無料電子書籍サイトから無料でダウンロードできます)から引用されています。

前述のように、ウィンドウ順序句は必須であり、SQL Serverでは、ORDER BY NULLなどの定数に基づく順序付けは許可されていません。しかし、驚くべきことに、定数を返すサブクエリ(たとえば、ORDER BY(SELECT NULL))に基づいて式を渡すと、SQL Serverはそれを受け入れます。同時に、オプティマイザーは式のネストを解除または展開し、すべての行で順序が同じであることを認識します。したがって、入力データから順序付け要件が削除されます。この手法を示す完全なクエリを次に示します。

SELECT actid, tranid, val,
 ROW_NUMBER() OVER(ORDER BY (SELECT NULL)) AS rownum
FROM dbo.Transactions;

enter image description here

インデックススキャンイテレータのプロパティで、OrderedプロパティがFalseであることを確認します。これは、イテレータがインデックスキーの順序でデータを返す必要がないことを意味します。


上記は、一定の順序付けを使用している場合は実行されないことを意味します。 Itzik Ben-Ganが、ウィンドウ関数がどのように機能するか、および使用される場合のさまざまなケースを最適化する方法について詳しく説明している本を読むことを強くお勧めします。

45
gotqn

order by 1だけを試してください。エラーメッセージを読んでください。次に、order by (select 1)を復元します。これを書いた人は誰でも、ある時点でエラーメッセージを読んでから、正しいことは、エラーを警告しようとしていた基本的な真実を理解するのではなく、システムをだましてエラーを発生させないことであると判断しました。

テーブルには固有の順序はありません。信頼できる何らかの形式の順序が必要な場合は、各行が一意に識別および順序付けされるように、任意のORDER BY句に十分な決定論的式を提供する必要があります。

システムをだましてエラーを発生させないなど、他のすべてはhoping提供されたツールを使用せずにシステムが賢明なことを行う保証賢明なことを行う-適切に指定されたORDER BY句。

任意のリテラル値を使用できます

ex

order by (select 0)

order by (select null)

order by (select 'test')

詳細についてはこちらを参照してください https://exploresql.com/2017/03/31/row_number-function-with-no-specific-order/

4
Madhivanan