什么是让使用id / PARENT_ID模型在MySQL / PHP中记录的所有父母最简单的方法?(

2019-09-17 00:39发布

我在寻找递归得到使用邻接表/单表继承模型(一个数据库中的所有父元素的最简单的方法id, parent_id )。

我目前选择看起来是这样的:

$sql = "SELECT
             e.id,
             TIME_FORMAT(e.start_time, '%H:%i') AS start_time,
             $title AS title,
             $description AS description,
             $type AS type,
             $place_name AS place_name,
             p.parent_id AS place_parent_id,
             p.city AS place_city,
             p.country AS place_country
         FROM event AS e
         LEFT JOIN place AS p ON p.id = e.place_id                          
         LEFT JOIN event_type AS et ON et.id = e.event_type_id
         WHERE e.day_id = '$day_id'
         AND e.private_flag = 0
         ORDER BY start_time";

每个event链接到一个place ,每个place可以是其他的孩子place (高达约5级深)

这可能在一个单一的与MySQL选择?

目前,我想这可能是一个单独的功能,通过返回循环$events阵列,增加place_parent_X元素,因为它去,但我不知道如何实现这一点。

Answer 1:

这是可能做到这一点在MySQL ,但你需要创建一个函数,并在查询中使用英寸

请参阅我的博客详细解释此项:

  • 在分层查询MySQL

下面是功能和查询:

CREATE FUNCTION hierarchy_connect_by_parent_eq_prior_id(value INT) RETURNS INT
NOT DETERMINISTIC
READS SQL DATA
BEGIN
        DECLARE _id INT;
        DECLARE _parent INT;
        DECLARE _next INT;
        DECLARE CONTINUE HANDLER FOR NOT FOUND SET @id = NULL;

        SET _parent = @id;
        SET _id = -1;

        IF @id IS NULL THEN
                RETURN NULL;
        END IF;

        LOOP
                SELECT  MIN(id)
                INTO    @id
                FROM    place
                WHERE   parent = _parent
                        AND id > _id;
                IF @id IS NOT NULL OR _parent = @start_with THEN
                        SET @level = @level + 1;
                        RETURN @id;
                END IF;
                SET @level := @level - 1;
                SELECT  id, parent
                INTO    _id, _parent
                FROM    place
                WHERE   id = _parent;
        END LOOP;
END

SELECT  id, parent
FROM    (
        SELECT  hierarchy_connect_by_parent_eq_prior_id(id) AS id, @level AS level
        FROM    (
                SELECT  @start_with := 0,
                        @id := @start_with,
                        @level := 0
                ) vars, t_hierarchy
        WHERE   @id IS NOT NULL
        ) ho
JOIN    place hi
ON      hi.id = ho.id

后者查询将选择一个给定节点的所有后代(你应该在设置@start_with变量)

要了解你可以使用一个简单的查询功能,没有一个给定节点的所有祖先:

SELECT  @r AS _id,
        @r := (
        SELECT  parent
        FROM    place
        WHERE   id = _id
        ) AS parent
FROM    (
        SELECT  @r := @node_id
        ) vars,
        place

这篇文章在我的博客中详细描述此查询:

  • 排序名单

对于这两种解决方案,在合理的时间工作,你需要有两个索引idparent

确保您的id被定义为PRIMARY KEY ,你有一个seconday指数parent



Answer 2:

这是不可能的标准亲子DB设计。

但是,你可以使用嵌套组在一个查询方法,并做到这一点,尽管这将需要相当多的工作来获取到这一点。



Answer 3:

貌似最简单的就是嵌套集合 。



文章来源: What is the simplest way to get all the parents of a record using the id / parent_id model in mysql/php?