你的SQL查詢 `
select *<br>FROM teacher<br>WHERE DATE_FORMAT(DATE_ADD('2023-11-01', INTERVAL FLOOR(RAND() * datediff(CURDATE(), '2023-11-01')) DAY), '%Y-%m') = DATE_FORMAT(create_time, '%Y-%m');
登錄后復(fù)制
` 意圖從給定月份到現(xiàn)在的時(shí)間段內(nèi)隨機(jī)查詢某個(gè)月的數(shù)據(jù),但返回的結(jié)果卻有出入。
問題根源
問題在于sql語句中的RAND()函數(shù)。它在每一次WHERE查詢時(shí)都會(huì)重新執(zhí)行,導(dǎo)致隨機(jī)日期范圍每次都不同。這樣一來,查詢結(jié)果就難以預(yù)測。
解決方案
解決這個(gè)問題的方法是在MySQL 8中使用WITH語句,將RAND()函數(shù)的執(zhí)行限制為一次。修改后的SQL語句如下:
`
WITH mo1 AS (<br> SELECT DATE_FORMAT(DATE_ADD('2023-11-01', INTERVAL FLOOR(RAND() * DATEDIFF(CURDATE(), '2023-11-01')) DAY), '%Y-%m') AS month<br>)<br>SELECT *<br>FROM teacher<br>JOIN mo1 ON mo1.month = DATE_FORMAT(create_time, '%Y-%m');<br>
登錄后復(fù)制
`
優(yōu)化建議
雖然這種方法可以解決問題,但仍有改進(jìn)的空間:
- 將動(dòng)態(tài)生成的日期范圍作為參數(shù)傳入SQL語句,而不是直接寫在SQL語句中,這可以提高代碼的可讀性和可維護(hù)性。
- 避免使用DATE_FORMAT()函數(shù)對查詢列進(jìn)行格式化,因?yàn)樗鼤?huì)影響MySQL使用索引的能力。轉(zhuǎn)而使用外部傳入的參數(shù)對日期進(jìn)行格式化或直接使用BETWEEN查詢會(huì)提高查詢效率。