簡體   English   中英

MySQL5.7表中遞歸搜索

[英]Search recursively in MySQL5.7 table

我有一個parameters表,如下所示:

ID 價值
參數0 1 + $(param1)
參數1 1 + $(param2) + $(param3)
參數2 1 + $(param4)
參數4 1 + 3
參數 3 1 + 2

我試圖編寫一個查詢來獲取param0中使用的參數列表。

預期輸出為:

ID
參數1
參數2
參數 3
參數4

解釋:

param0包含param1所以需要在param1中搜索

param1包含param2param3所以需要在param2 , param3中搜索

param2包含param4所以需要在param4中搜索

param3param4不包含任何參數,因此搜索將在此處停止。

db小提琴

CREATE PROCEDURE get_params_list (param VARCHAR(255))
BEGIN
CREATE TABLE params_list (param VARCHAR(255) PRIMARY KEY,
                          param_value VARCHAR(255)) ENGINE = Memory;
INSERT INTO params_list 
SELECT *
FROM parameters
WHERE parameters.param = param;
REPEAT
    INSERT IGNORE INTO params_list
    SELECT parameters.*
    FROM params_list
    JOIN parameters ON LOCATE(CONCAT('$(', parameters.param, ')'),
                              params_list.param_value);
UNTIL NOT ROW_COUNT() END REPEAT;
SELECT params_list.param 
FROM params_list
WHERE params_list.param <> param;
DROP TABLE params_list;
END

https://dbfiddle.uk/?rdbms=mysql_5.7&fiddle=2f51944e354f92cfe7d428ce84f46184

沒有存儲過程,最高級別為 3:

SET @search = 'param';

CREATE TEMPORARY TABLE Ptemp
   SELECT PARAM, P
   FROM (
      SELECT 
         PARAM,
         PARAM_VALUE,
         x.x,
         substring_index(substring_index(replace(PARAM_VALUE,')','('),'(',x.x),'(',-1) as P
      FROM parameters 
      CROSS JOIN (select 1 as x union
            select 2 as x union
            select 3 as x union
            select 4 as x ) x 
     ) x 
   WHERE P LIKE 'param%' 
;

CREATE TEMPORARY TABLE Ptemp1 as SELECT * FROM Ptemp;
CREATE TEMPORARY TABLE Ptemp2 as SELECT * FROM Ptemp;
CREATE TEMPORARY TABLE Ptemp3 as SELECT * FROM Ptemp;
CREATE TEMPORARY TABLE Ptemp4 as SELECT * FROM Ptemp;
CREATE TEMPORARY TABLE Ptemp5 as SELECT * FROM Ptemp;

select P from Ptemp WHERE PARAM=@search
union all
select P from Ptemp1 WHERE PARAM IN (select P 
                                     from Ptemp2 
                                     WHERE PARAM=@search)
union all
select P from Ptemp3 WHERE PARAM IN (select P 
                                     from Ptemp4 
                                     WHERE PARAM IN (select P 
                                                     from Ptemp5 
                                                     WHERE PARAM=@search))

見: DBFIDDLE

DB-FIDDLE

需要臨時表的(多個)副本,因為 MySQL 在重新使用臨時表時會給出此錯誤:

查詢錯誤:錯誤:ER_CANT_REOPEN_TABLE:無法重新打開表:'Ptemp1'

結論:編寫存儲過程是要走的路,至少在 MySQL 8.0 之前的版本中是這樣。

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM