ORDER BY RAND()
DBMSは、数行だけを保持するために、すべての行を読み取り、すべてを並べ替える必要があるため、低速です。したがって、このクエリのパフォーマンスはテーブルの行数に大きく依存し、行数が増えると低下します。
それを最適化する方法はありません。
ただし、別の方法があります:
「ランダムな5行を取得」を実装できます 6つのクエリを実行する:
- テーブルの行数を取得します(これはキャッシュできます)
-
OFFSET <random offset from 0 to $number_of_rows-1> LIMIT 1
で5つのクエリを実行します (つまり、ランダムなオフセットから1行だけを読み取って返します)例:
SELECT * FROM Products OFFSET 42 LIMIT 1
(注:今のところ、参加せずに)このようなクエリは非常に高速で、テーブルのサイズに実質的に依存しない時間で実行されます。
これは多くである必要があります ORDER BY RAND()
よりも高速 。
次に、ランダムな製品ごとにランダムな画像を取得します。
SELECT *
FROM (
SELECT *
FROM Products
OFFSET 42 LIMIT 1
) p
JOIN ProductImages pi
ON pi.product_id = p.id
ORDER BY RAND()
LIMIT 1
内側のクエリは依然として高速であり、外側のクエリは数行しか並べ替えていないため(製品ごとの画像が少ないと想定)、rand()による順序を使用できます。