MySQL を使用しているため、最初にテーブルからカウントを取得し、次にそのカウントに基づいてランダムなオフセットを選択する次の SQL クエリを試すことができます。次に、計算されたオフセットを使用できるようにステートメントを準備し、ステートメントを実行します。
SELECT @count := COUNT(*) FROM table AS a JOIN table AS b ON ( a.id <> b.id ) WHERE (a.data1=1 AND b.data1=1) AND ABS( a.rating - b.rating ) <100;
SET @offset = CONVERT(FLOOR(RAND() * @count), SIGNED);
PREPARE mystatement FROM "SELECT
a.id as aid, a.data1 as adata1, a.data2 as adata2
b.id as bid, b.data1 as bdata1, b.data2 as bdata2
FROM table AS a
JOIN table AS b ON ( a.id <> b.id )
WHERE (a.data1=1 AND b.data1=1) AND ABS( a.rating - b.rating ) <100 LIMIT ?, 1";
EXECUTE mystatement USING @offset;
DEALLOCATE PREPARE mystatement;
大規模なデータセットでは、よりも高速に実行する必要がありますORDER BY RAND()
。試してみて、私に知らせてください... ;-)
編集
クエリは phpmyadmin で使用すると機能しないため、MySQL コンソールを使用してクエリを実行するか、2 つのオプションがある php スクリプトを作成します。最初のオプションは mysql に作業を任せることです。
mysql_query('SELECT @count := COUNT(*) FROM table AS a JOIN table AS b ON ( a.id <> b.id ) WHERE (a.data1=1 AND b.data1=1) AND ABS( a.rating - b.rating ) <100');
mysql_query('SET @offset = CONVERT(FLOOR(RAND() * @count), SIGNED)');
mysql_query('PREPARE mystatement FROM "SELECT
a.id as aid, a.data1 as adata1, a.data2 as adata2
b.id as bid, b.data1 as bdata1, b.data2 as bdata2
FROM table AS a
JOIN table AS b ON ( a.id <> b.id )
WHERE (a.data1=1 AND b.data1=1) AND ABS( a.rating - b.rating ) <100 LIMIT ?, 1"');
$res = mysql_query('EXECUTE mystatement USING @offset');
$row = mysql_fetch_assoc($res);
print_r($row);
さらに高速になる可能性がある 2 番目のオプションは、MySQL で作業の一部を実行し、プログラミング言語 (この場合は PHP) で他の部分を実行することで構成されます。
$res = mysql_query("SELECT COUNT(*) FROM table AS a JOIN table AS b ON ( a.id <> b.id ) WHERE (a.data1=1 AND b.data1=1) AND ABS( a.rating - b.rating ) <100')");
$row = mysql_fetch_array($res);
$offset = rand(0, $row[0]-1);
$res = mysql_query("SELECT
a.id as aid, a.data1 as adata1, a.data2 as adata2
b.id as bid, b.data1 as bdata1, b.data2 as bdata2
FROM table AS a
JOIN table AS b ON ( a.id <> b.id )
WHERE (a.data1=1 AND b.data1=1) AND ABS( a.rating - b.rating ) <100 LIMIT $offset, 1");
$row = mysql_fetch_assoc($res);
私が見つけた ORDER BY RAND() を高速化する別の方法は、次のようなクエリで構成されています。
SELECT
a.id as aid, a.data1 as adata1, a.data2 as adata2
b.id as bid, b.data1 as bdata1, b.data2 as bdata2
FROM table AS a
JOIN table AS b ON ( a.id <> b.id )
WHERE (RAND() < (SELECT ((1/COUNT(*))*10) FROM table AS a JOIN table AS b ON ( a.id <> b.id ) ) )
AND (a.data1=1 AND b.data1=1) AND ABS( a.rating - b.rating ) <100
ORDER BY RAND()
LIMIT 1
あなたが得た結果について私に更新することを忘れないでください;-) .