隨機抽樣是 A/B 測試、推薦系統、審核抽查的常見需求。各資料庫語法差異極大,本文整理標準寫法與效能備註。
| 資料庫 | 語法 | 範例(取 50 筆) | 效能備註 |
|---|---|---|---|
| SQL Server | ORDER BY NEWID() | SELECT TOP 50 * FROM TAB_USERS ORDER BY NEWID(); | 全表掃描 + 排序,大表慎用 |
| Oracle | DBMS_RANDOM.VALUE + 子查詢 | SELECT * FROM (SELECT * FROM TAB_USERS ORDER BY DBMS_RANDOM.VALUE) WHERE ROWNUM <= 50; | 同樣全表排序 |
| MySQL | ORDER BY RAND() | SELECT * FROM TAB_USERS ORDER BY RAND() LIMIT 50; | 臨時表 + filesort,極慢 |
| PostgreSQL | ORDER BY RANDOM() | SELECT * FROM TAB_USERS ORDER BY RANDOM() LIMIT 50; | 同 MySQL |
| Access | ORDER BY RND(欄位) | SELECT TOP 50 * FROM TAB_USERS ORDER BY RND(id); | 需傳入正數種子 |
-- SQL Server (TABLESAMPLE 10 PERCENT)
SELECT * FROM TAB_USERS TABLESAMPLE (10 PERCENT) REPEATABLE (12345);
-- 先取 MAX(id),再在應用層產生隨機 ID 清單,最後 WHERE id IN (...)
rand_sort INT,定期批次更新 rand_sort = RAND() * 2147483647,查詢時 ORDER BY rand_sort 瞬間完成。Access SQL 中 RND([欄位]) 需傳入正數種子,ASP.NET 後端需動態生成:
var rnd = new Random(Guid.NewGuid().GetHashCode());
int seed = rnd.Next();
string sql = $"SELECT TOP 50 * FROM TAB_USERS ORDER BY RND({seed} * [id])";
ORDER BY RAND()/NEWID()/RANDOM()。TABLESAMPLE / 主鍵範圍抽樣 / 預計算隨機欄位。根據資料量與精確度需求選擇適當策略,避免 ORDER BY RAND() 癱瘓生產庫。