2013-04-03 119 views
0

我的表有8個VARCHAR字段,每個字符串的64位二進制字符串。我的目標是爲每個註冊獲得Hamming distance。我是這樣做的下一個查詢:MySQL:高效的二進制值比較

SELECT 
BIT_COUNT(CONV(fp.bin_str0, 2, 10)^CONV('0000000001101111000000000101011100000000001010100000000001111101', 2, 10)) + 
BIT_COUNT(CONV(fp.bin_str1, 2, 10)^CONV('0000000010110001000000001000000000000000011000010000000011110100', 2, 10)) + 
BIT_COUNT(CONV(fp.bin_str2, 2, 10)^CONV('0000000010010100000000000010101100000000110001000000000011100100', 2, 10)) + 
BIT_COUNT(CONV(fp.bin_str3, 2, 10)^CONV('0000000011101011000000000001110000000000101100010000000000011001', 2, 10)) + 
BIT_COUNT(CONV(fp.bin_str4, 2, 10)^CONV('0000000000010000000000000011010100000000111011100000000001001101', 2, 10)) + 
BIT_COUNT(CONV(fp.bin_str5, 2, 10)^CONV('0000000000101111000000000110101000000000000010100000000000101101', 2, 10)) + 
BIT_COUNT(CONV(fp.bin_str6, 2, 10)^CONV('0000000000011000000000000101011000000000001010000000000000001011', 2, 10)) + 
BIT_COUNT(CONV(fp.bin_str7, 2, 10)^CONV('0000000000101011000000000011100100000000000100000000000000111010', 2, 10)) from mytable fp 

所以這個查詢是非常緩慢的。有一些原因:mytable有3M寄存器,並且fp.bin_stri字段是VARCHAR類型。

由於MySQL有BINARY類型,我可以通過fp.bin_stri的BINARY類型執行相同的查詢嗎?怎麼樣?

我很困惑,因爲當我將fp.bin_stri更改爲BINARY時,此字段的數據顯示爲BLOB,現在我不知道查詢應該如何。它應該使用CONV

回答

2

64位二進制字符串的大小與MySQL的BIGINT類型(雙精度浮點數或長整數現代硬件上的標準大小)相同。使用BIGINT UNSIGNED來存儲每個字段,然後可以使用b'1010...'語法而不是CONV()來比較其他位字段。

BIT_COUNT(fp.strN^b'0000000001101111000000000101011100000000001010100000000001111101') 

由於硬件設計爲在64位值上執行位操作,因此應該是非常快的。

+0

而當我向數據庫插入一個新值時,該如何施放它?將它作爲BINARY插入就足夠了嗎? – andriy

+0

如果要插入1和0的序列,可以使用二進制文字語法「b''」。 'INSERT INTO mytable(str1,...)VALUES(b'1010',...)'。 –

+0

我應該補充一點,如果你需要頻繁地加載整個表,LOAD DATA INFILE會快很多,但是你需要將二進制字段表示爲文件中的無符號整數。請參閱http://dev.mysql.com/doc/refman/5.5/en/load-data.html。 –