背景
偶然需要在數據庫來實現部分功能學習了一下mysql的存儲過程,感覺還蠻有意思的。
需求是:
獲取傳入字符串與數據庫中對應字段的相似程度。
實現一個取表中字符串數據,循環比較傳入數據與表中數據相同位的個數,取出相似的對應值,作爲查詢條件,返回查詢結果。
知識積累
#當存儲過程存在的時候刪除
DROP PROCEDURE IF EXISTS imageserch;
#創建存儲過程,可以是有參的,可以是無參的
#語法:CREATE PROCEDURE([[IN |OUT |INOUT ] 參數名 數據類形...])
#IN參數的值必須在調用存儲過程時指定,在存儲過程中修改該參數的值不能被返回,爲默認值
#OUT:該值可在存儲過程內部被改變,並可返回
#INOUT:調用時指定,並且可被改變和返回
CREATE PROCEDURE imageserch (
IN dnacompare VARCHAR (30) #指定一個字符串的入參
)
#begin和end之間是存儲過程的實現
BEGIN
#開始首先也是定義變量,用於存儲查詢結果,中間過程的變量等
#DECLARE variable_name [,variable_name...] datatype [DEFAULT value];
#數據類型:int, float, date, varchar(length)
DECLARE
dnasource VARCHAR (30);
DECLARE
a VARCHAR (30);
DECLARE
b VARCHAR (30);
DECLARE
i INT;
DECLARE
deff INT DEFAULT 0;
#這個用於處理遊標到達最後一行的情況
DECLARE
done INT DEFAULT 0;
#聲明遊標cursor_name(cursor_name是個多行結果集)
#這裏使用遊標來遍歷表中數據
DECLARE
cursor_pic CURSOR FOR SELECT
dna
FROM
pic_work;
#設置一個終止標記(如果不要這句,會出現1329 - No data - zero rows fetched, selected, or processed錯誤信息)
#DECLARE CONTINUE HANDLER FOR SQLSTATE '02000' SET done = 1;
DECLARE
CONTINUE HANDLER FOR NOT FOUND
SET done = 1;
#打開遊標
OPEN cursor_pic;
#開始循環,判斷是否遊標已經到達了最後作爲循環條件
#while ... do ... end while
#repeat... end repeat
#REPEAT
WHILE done <> 1 DO
#獲取遊標當前指針的記錄,讀取一行數據並傳給變量 dnasource
#下面兩種寫法都可以獲取到遊標當前的值
#FETCH next From cursor_pic INTO dnasource;
FETCH cursor_pic INTO dnasource;
#輸出查出來的數據,可以使用SELECT進行變量的輸出,方便調試
#SELECT dnasource;
SET deff = 0;
SET i = 0;
#遍歷該輸入數據與遊標獲取的數據庫數據相似程度,使用循環
WHILE i < CHAR_LENGTH(dnasource) DO
SET a = SUBSTRING(dnasource, i, i + 1);
SET b = SUBSTRING(dnacompare, i, i + 1);
#使用IF判斷
IF a != b THEN
SET deff = deff + 1;
END IF;
#增加循環變量
SET i = i + 1;
END WHILE;
#IF的嵌套
#if ... then ... else ... end if
IF done <> 1 THEN
IF deff <= 5 THEN
INSERT INTO pic_work_temp (dna)
VALUES
(dnasource);
COMMIT;
#SELECT deff;
END IF;
END IF;
#UNTIL done
#END
#REPEAT
END
WHILE;
#關閉遊標
CLOSE cursor_pic;
#SELECT dna FROM pic_work_temp;
SELECT
*
FROM
pic_work
WHERE
dna IN (SELECT dna FROM pic_work_temp);
TRUNCATE TABLE pic_work_temp;
END
#調用存儲過程
call imageserch("1210101");
執行結果
常用字符串函數
CHARSET(str) //返回字串字符集
CONCAT (string2 [,… ]) //連接字串
INSTR (string ,substring ) //返回substring首次在string中出現的位置,不存在返回0
LCASE (string2 ) //轉換成小寫
LEFT (string2 ,length ) //從string2中的左邊起取length個字符
LENGTH (string ) //string長度
LOAD_FILE (file_name ) //從文件讀取內容
LOCATE (substring , string [,start_position ] ) 同INSTR,但可指定開始位置
LPAD (string2 ,length ,pad ) //重複用pad加在string開頭,直到字串長度爲length
LTRIM (string2 ) //去除前端空格
REPEAT (string2 ,count ) //重複count次
REPLACE (str ,search_str ,replace_str ) //在str中用replace_str替換search_str
RPAD (string2 ,length ,pad) //在str後用pad補充,直到長度爲length
RTRIM (string2 ) //去除後端空格
STRCMP (string1 ,string2 ) //逐字符比較兩字串大小,
SUBSTRING (str , position [,length ]) //從str的position開始,取length個字符
默認第一個字符下標爲1,即參數position必須大於等於1