3

役割に基づいてメニューとサブメニューを取得しようとしています(他の表で指定)。役割に基づいて、例。MenuIDs: 1,2,5 を選択した場合、M1、M2、および M3 のすべてのサブメニューを取得する必要があります。MenuParentID は、親の MenuId を指定します。

 MenuID MenuParentID   MenuName           MenuNavigateUrl       HasSubMenus 
 1      -1             M1                 1.aspx                0 
 2      -1             M2                 #                     1 
 3       2             M2.1               2.aspx                0 
 4       2             M2.2               3.aspx                0 
 5      -1             M3                 #                     1 
 6       5             M3.1               #                     1
 7       5             M3.2               #                     1 
 8       6             M3.1.1             4.aspx                0 
 9       6             M3.1.2             5.aspx                0 
10       7             M3.2.1             6.aspx                0 
11       7             M3.2.2             7.aspx                0 
12      -1             M4                 #                     1 
13      12             M4.1               8.aspx                0 
14      12             M4.2               9.aspx                0 

これが私がしたことです:

DELIMITER $$

DROP FUNCTION IF EXISTS `myDB`.`GetPermissions`$$

CREATE DEFINER=`root`@`%` FUNCTION `GetPermissions`(
rootMenuID int(11)
) RETURNS varchar(200) CHARSET latin1
BEGIN
DECLARE menuIdList VARCHAR(100);
DECLARE menu_id INT(11);
DECLARE record_not_found INT DEFAULT 0;
DECLARE getMenuCursor CURSOR FOR SELECT DISTINCT(MenuId) FROM MenuIdListTable;
DECLARE CONTINUE HANDLER FOR NOT FOUND SET record_not_found = 1; 
CREATE TEMPORARY TABLE MenuIdListTable(MenuId INT(11) NULL);
SET menuIdList = ',';
IF((SELECT COUNT(*) FROM menus WHERE MenuParentID = rootMenuID) > 0) THEN
    INSERT INTO MenuIdListTable(MenuID) SELECT MenuID FROM menus WHERE    
MenuParentID = rootMenuID; 
    OPEN getMenuCursor;
    read_loop: LOOP
        FETCH getMenuCursor INTO menu_id;
        IF record_not_found THEN 
           LEAVE read_loop; 
        END IF;
        SET menuIdList = CONCAT(menuIdList,menu_id,',');
    END LOOP read_loop;
END IF;
DROP TEMPORARY TABLE MenuIdListTable;
SET menuIdList = SUBSTR(menuIdList,1,LENGTH(menuIdList)-1);
RETURN menuIdList;
END$$

DELIMITER ;

しかし、再帰ロジックを適用してすべてのサブメニューを取得することはできません。元。「M3」(MenuID = 5) の場合、サブメニュー「M3.1」および「M3.2」を取得しています。サブメニューではありません。つまり、「M3.1」の場合は「M3.1.1」、「M3.1.2」、「M3.2」の場合は「M3.2.1」、「M3.2.2」です。それらの1つにサブメニューがある場合も、問題は解決しません! 助けてください。

4

2 に答える 2

3

plsqlからの「事前に接続」する喜び、またはmysqlを欠いている他のデータベースからのCTE。

現在、私の脳には指定された mysql 関数を完全に解析する能力がないため、参照をスローするだけ です: http://explainextended.com/2009/03/17/hierarchical-queries-in-mysql/ mysqlの階層に関するいくつかの良い説明(時には悪... 1つの選択のみのツリー構造のように)

于 2012-08-04T07:37:23.713 に答える
1

このコードを試してください:

DROP TABLE IF EXISTS temp;
CREATE TABLE temp(id int,MenuID int,MenuName varchar(50),MenuParentID int,HasSubMenus int) SELECT (@id:=@id+1) as id,MenuID,MenuName,MenuParentID,HasSubMenus from menus,
(SELECT @id:=0) id where MenuParentID = 5;
select * from temp;
DROP TABLE IF EXISTS output;
CREATE TABLE output(MenuID int,MenuName varchar(50),MenuParentID int,HasSubMenus int) select MenuID,MenuName,MenuParentID,HasSubMenus from  temp;

SET @idmin = (SELECT min(id) from temp);
SET @idmax = (SELECT max(id) from temp);

WHILE @idmin <= @idmax DO

INSERT INTO output(MenuID,MenuName,MenuParentID,HasSubMenus)
select MenuID,MenuName,MenuParentID,HasSubMenus from  menus where MenuParentID=(select MenuID from temp where id = @idmin);

SET @idmin=@idmin+1;

END WHILE;

select (@id:=@id) as id1,GROUP_CONCAT(MenuName,',') from output, (SELECT @id:=1) id1 group by id1;
于 2012-08-04T11:27:29.600 に答える