您好,登錄后才能下訂單哦!
不知道大家之前對類似MYSQL的floor出現報錯如何解決的文章有無了解,今天我在這里給大家再簡單的講講。感興趣的話就一起來看看正文部分吧,相信看完MYSQL的floor出現報錯如何解決你一定會有所收獲的。
利用語句網上一搜一大堆,我就不再細說了,先根據一個語句上個總結圖片吧:
先把rand函數說一下,下面會用到。
語句中的floor(rand(0)*2)是什么意思?是為了產生一個不唯一的且能會出現重復的數字。rand()函數產生的數會隨機產生0到1的小數,而加上參數變成rand(0)的時候,會產生一個確定的小數(我的理解)可能有些繞, 所以我們看一下執行語句:
rand()函數執行2次結果,:
加了參數執行2次的結果:
所以,rand(0)是為了得到一個確定的數,也就是執行第幾次就是什么數據(我自己的理解),而*2再floor是為了得到唯一的整數數據,不然小數太長了,想找到個重復的數就太難了。。除此之外你乘大于等于2的什么數都行,當然也不能太大,比如9999999999999。要大于等于2是因為,小于2,floor(rand(0)*2)會變成0,不會不唯一,數太大,,沒有那么多數據能讓你查到重復。。。
再說報錯,報了什么錯呢,是主鍵重復,為什么會主鍵重復呢?這就group by 和 count(*)有關了,我們先看count(*)和group by組合一起的效果
結果會顯示每個列的次數,而這個列的內容,是唯一的主鍵。而在查詢過程中,是先建立一張虛擬表,一行一行插入的,而插入時已經有重復主鍵了,那么,就會報錯。當然,可能會問了,重復時,count(*)就加1了,為什么會主鍵重復呢?這就和rand()函數有關了,官方文檔中提到,rand()函數在進行GROUP BY查詢時會被計算多次,這里列舉參考文檔的解釋,我覺得說的很清楚:
1.查詢前默認會建立空虛擬表
2.取第一條記錄,執行floor(rand(0)*2),發現結果為0(第一次計算),查詢虛擬表,發現0的鍵值不存在,則floor(rand(0)*2)會被再計算一次,結果為1(第二次計算),插入虛表,這時第一條記錄查詢完畢
3.查詢第二條記錄,再次計算floor(rand(0)*2),發現結果為1(第三次計算),查詢虛表,發現1的鍵值存在,所以floor(rand(0)*2)不會被計算第二次,直接count(*)加1,第二條記錄查詢完畢
4.查詢第三條記錄,再次計算floor(rand(0)*2),發現結果為0(第4次計算),查詢虛表,發現鍵值沒有0,則數據庫嘗試插入一條新的數據,在插入數據時floor(rand(0)*2)被再次計算,作為虛表的主鍵,其值為1(第5次計算),然而1這個主鍵已經存在于虛擬表中,而新計算的值也為1(主鍵鍵值必須唯一),所以插入的時候就直接報錯了。
5.整個查詢過程floor(rand(0)*2)被計算了5次,查詢原數據表3次,所以這就是為什么數據表中需要3條數據,使用該語句才會報錯的原因。
這里補充一下5,為什么需要3條數據,看一下floor(rand(0)*2)的執行結果
雖然只有2個值,但是你要查到第三條才會有重復啊~~~~~
好了,最后可以總結一下,SELECT distinct concat(0x23,PersonID,0x3a,Password,0x23) FROM person limit 0,1就是查想要的數據,floor(rand(0) * 2)是為了生成一個不唯一的且可重復的數,好讓后面能主鍵重復
concat((SELECT distinct concat(0x23,PersonID,0x3a,Password,0x23) FROM person limit 0,1 ),rand(0) * 2 ),是為了聚合成#1:c4d7b26adbecfc3fedbc895f30099f4b#1的樣子,SELECTcount(*), concat( (SELECT distinct concat(0x23,PersonID,0x3a,Password,0x23) FROM person limit 0,1),floor(rand(0) * 2)) xFROMinformation_schema. TABLES GROUP BY x 是為了把rand count(*),group by湊在一起,因為湊在一起才會計算多次,有主鍵重復。最外面那層select 1 可以不要。。
看完MYSQL的floor出現報錯如何解決這篇文章,大家覺得怎么樣?如果想要了解更多相關,可以繼續關注我們的行業資訊板塊。
免責聲明:本站發布的內容(圖片、視頻和文字)以原創、轉載和分享為主,文章觀點不代表本網站立場,如果涉及侵權請聯系站長郵箱:is@yisu.com進行舉報,并提供相關證據,一經查實,將立刻刪除涉嫌侵權內容。