ランダムなレコードを取得したいレコードでいっぱいのテーブルがあったとしましょう。ただし、そのテーブルの特定の行を他の行よりも頻繁に表示する必要があります(どの行がユーザーによって異なるか)。SQLを使用してこれを行うための最良の方法は何ですか?
私が考えることができる唯一の方法は、一時テーブルを作成し、より一般的にしたい行で埋めてから、テーブルからランダムに選択された他の行で埋めることです。もっと良い方法はありますか?
ランダムなレコードを取得したいレコードでいっぱいのテーブルがあったとしましょう。ただし、そのテーブルの特定の行を他の行よりも頻繁に表示する必要があります(どの行がユーザーによって異なるか)。SQLを使用してこれを行うための最良の方法は何ですか?
私が考えることができる唯一の方法は、一時テーブルを作成し、より一般的にしたい行で埋めてから、テーブルからランダムに選択された他の行で埋めることです。もっと良い方法はありますか?
私が考えることができる1つの方法は、ウェイトのローリング合計である別の列をテーブルに作成し、0からすべてのウェイトの合計までの乱数を生成してレコードをプルし、ローリングが最も高い行をプルすることです。乱数よりも小さい合計値。
たとえば、次の重みを持つ4つの行がある場合:
+---+--------+------------+
|row| weight | rollingsum |
+---+--------+------------+
| a | 3 | 3 |
| b | 3 | 6 |
| c | 4 | 10 |
| d | 1 | 11 |
+---+--------+------------+
次に、0から11までの乱数を選択し、、、などの場合はn
行を返します。a
0<=n<3
b
3<=n<6
ローリングサムの生成に関するリンクは次のとおりです。
http://dev.mysql.com/tech-resources/articles/rolling_sums_in_mysql.html
http://dev.mysql.com/tech-resources/articles/rolling_sums_in_mysql_followup.html
SQLだけで簡単にできるかどうかはわかりません。T-SQLなどを使用すると、行を複製するループを作成することも、SQLを使用して、代わりに行の複製を実行するための命令を生成することもできます。
私はあなたの確率モデルを知りませんが、後者を達成するためにこのようなアプローチを使用することができます。これらのテーブル定義を考えると:
RowSource
---------
RowID
UserRowProbability
------------------
UserId
RowId
FrequencyMultiplier
次のようなクエリを作成できます(SQL Server固有)。
SELECT TOP 100 rs.RowId, urp.FrequencyMultiplier
FROM RowSource rs
LEFT JOIN UserRowProbability urp ON rs.RowId = urp.RowId
ORDER BY ISNULL(urp.FrequencyMultiplier, 1) DESC, NEWID()
これにより、行のランダムなセットと、繰り返す必要のある行の数を選択できます。次に、アプリケーションロジックで、行の複製を実行し、結果をシャッフルできます。
ユーザー、データ、ユーザーデータの3つのテーブルから始めます。ユーザーデータには、各ユーザーに優先する行が含まれています。
次に、ユーザーが好むデータ行に基づいて1つのビューを作成します。
優先されないデータを持つ2番目のビューを作成します。
最初の2つのユニオンである3番目のビューを作成します。ユニオンは、優先データからさらに行を選択する必要があります。
次に、最後に3番目のビューからランダムな行を選択します。