我已經RAND()和它的性能問題,閱讀有關訂單 - 做這些只適用於返回大數據集的查詢?舉例來說,如果我有10萬行的表,並且使用WHERE子句返回10條記錄的數據集,然後使用ORDER BY RAND()LIMIT 1,經過我的表已經滲透到將這個ORDER BY RAND()被應用記錄匹配WHERE子句,因此具有可忽略的性能問題?MySQL ORDER BY RAND()函數何時排序?
回答
你說得對,它會與WHERE,GROUP BY減少的行數和HAVING後應用ORDER BY。但它會在LIMIT之前應用ORDER BY。
因此,如果您篩選的行數下降充分,那麼,在ORDER BY RAND()可以達到你想要的東西沒有一個偉大的業績影響。代碼的合法利益很簡單,易於閱讀。
當您的認爲您的查詢應該將行數減少到某個較小值時,就會出現問題,但隨着數據量的增長,需要排序的行數再次變大。由於您的查詢,則不會對排序結果LIMIT 10隱藏,你BY RAND()上的50萬行執行訂單的事實。你只是看到神祕的表現越來越糟。
我已經寫了有關替代方法在我的書SQL Antipatterns: Avoiding the Pitfalls of Database Programming,或在這裏其他的答案對堆棧溢出選擇一個隨機行:
RAND()
值將針對每一行進行計算,因此對於大型數據集不是非常有效,LIMIT
子句不會更改該值。要解決這個通常的方法是計算提前一個隨機數,然後檢索基於一些預生成索引列與之對應的行。
這裏有一個詳細的解釋:
不要緊,你有多少行選擇。如果ORDER BY RAND()
爲表中的每一行計算一個隨機數。這是因爲它必須計算每一行的隨機值才能知道哪一行產生了最大的值。所以,如果你有10萬行的表,然後調用ORDER BY RAND() LIMIT 1
你告訴MySQL來產生一個隨機數爲100,000行,由數排序,然後給你的第一個。
這是很要快得多:從Table
SELECT COUNT(*)生成的腳本/編程語言0和上面的查詢結果減去1之間的隨機數。
SELECT * FROM
Table
LIMIT random_number_here,1
基於快速測試,我必須得出結論,ORDER BY RAND()僅適用於後應用WHERE語句,而不是整個數據集。從表中
結果與50,000行:
SELECT * FROM `mytable` LIMIT 1 (1 total, Query took 0.0007 sec)
SELECT * FROM `mytable` WHERE First = 'Hilda' LIMIT 1 (1 total, Query took 0.0010 sec)
SELECT * FROM `mytable` WHERE First = 'Hilda' (142 total, Query took 0.0201 sec)
SELECT * FROM `mytable` WHERE First = 'Hilda' ORDER BY RAND() LIMIT 1 (1 total, Query took 0.0229 sec)
SELECT * FROM `mytable` WHERE First = 'Hilda' ORDER BY RAND() (142 total, Query took 0.0236 sec)
SELECT * FROM `mytable` ORDER BY RAND() LIMIT 1 (1 total, Query took 0.4224 sec)
- 1. 使用ORDER BY或PHP排序函數排序MySQL查詢
- 2. MYSQL排序GROUP BY
- 3. list by append函數不能按排序函數排序
- 4. mysql by count - 按值排序
- 5. 的MySQL GROUP BY與排序
- 6. MySQL的rand()函數BY
- 7. mySQL ORDER BY TODAY然後正常排序
- 8. PHP mysql使用ORDER BY DESC排序行
- 9. MySQL的GROUP BY和排序每組
- 10. MySQL排序SELECT by關聯列
- 11. MySQL的ORDER BY不排序正確
- 12. 是PHP排序比mysql「order by」更好?
- 13. mysql的排序問題與ORDER BY
- 14. SQL GROUP BY,HAVING和排序(MySQL的)
- 15. MySQL GROUP BY並按列排序組
- 16. MySQL - 按count()和GROUP BY排序
- 17. MySQL:通過兩列函數排序
- 18. 在MySQL組函數內排序
- 19. 嵌入函數後排序矩陣R
- 20. 排序GROUP BY agregats
- 21. 按聚合函數排序MySql
- 22. 基數排序,R
- 23. LINQ Group by排序
- 24. 排序函數不排序
- 25. 使用ORDER BY子句在MYSQL中排序數據
- 26. SQL Server ORDER BY - 排序排序方法
- 27. group by by by by mysql
- 28. mysql order by custom
- 29. MySQL的ORDER BY whatever_is_the_first_field DESC或反向的MySQL默認的排序
- 30. 如何在MySQL中對GROUP BY進行排序?
幾乎任何東西可以很快去的時候只能用小數據集進行操作,但在概念上一個LIMIT ORDER BY子句後適用。所以它取決於查詢優化器。爲什麼不試試一個測試數據庫? –
請參閱下面的實驗 - 將ORDER BY RAND()應用於WHERE子句返回的記錄的子集 - 對於返回143條記錄的記錄集,限制爲隨機記錄的時間可以忽略不計,而應用它對整個表沒有where子句花費了更多的時間。 – key2starz