MySql 更新行,它是 "Descendants"

标签 mysql sql-update hierarchical-data children

我无法弄清楚如何更新一行的后代/子代。 示例表,命名为 test

+----+--------+------+
| Id | Parent | Val  |
+----+--------+------+
|  1 |      0 |      |
|  2 |      1 |      |
|  3 |      1 |      |
|  4 |      1 |      |
|  5 |      0 |      |
|  6 |      5 |      |
|  7 |      6 |      |
|  8 |      6 |      |
|  9 |      0 |      |
+----+--------+------+

我想做的是,当 Val 设置为某项时,更新与该行相关的每一行。例如,如果我跑了

UPDATE test SET Val=1 WHERE Id=5;

我希望 Id 为 6、7 和 8 的行中的 Val 也为 1。

我能想到的最好的事情是

UPDATE test t1 
    JOIN test t2 ON t1.Id = t2.Parent 
    JOIN test t3 ON t2.Id = t3.Parent 
SET t1.Val=1, t2.Val=1, t3.Val=1 WHERE t1.Id=5;

+----+--------+------+
| Id | Parent | Val  |
+----+--------+------+
|  1 |      0 |      |
|  2 |      1 |      |
|  3 |      1 |      |
|  4 |      1 |      |
|  5 |      0 |   1  |
|  6 |      5 |   1  |
|  7 |      6 |   1  |
|  8 |      6 |   1  |
|  9 |      0 |      |
+----+--------+------+

这给了我想要的东西,但恐怕这是不好的做法,而且它不考虑可变深度。我可以在这里做什么?我认为触发器可能是答案,但这似乎是不可能的。我收到错误消息“无法更新存储函数/触发器中的表,因为它已被调用此存储函数/触发器的语句使用”

最佳答案

用 MySQL 处理这种情况非常尴尬,因为 MySQL doesn't support recursive queries .

我通过将层次结构存储为传递闭包来解决这个问题,而不是您使用的“parent_id”样式。请参阅我对 What is the most efficient/elegant way to parse a flat table into a tree? 的回答

然后您可以更新层次结构中给定节点的所有后代:

UPDATE test JOIN testclosure AS c ON test.id = c.descendant
SET test.val = 1
WHERE c.ancestor = 5;

关于MySql 更新行,它是 "Descendants",我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/25437587/

相关文章:

c++ - 像 MySQL 比较一样比较 MFC CString

mysql - SQL 使用 View 更新表

php - MySQL 单例类与递归函数冲突(PHP)

database - 除了 XML 之外,是否有可以轻松消化分层数据的数据库?

php - 选择不同的经度和纬度值并找到它们的中值

php - 复杂 MySQL 查询中的排序和分组

带有嵌套 FROM (SELECT) 的 php sql UPDATE

Mysql更新,选择替换长字符串中的指定字符

sql - Oracle SQL/PLSQL : Hierarchical recursive query with repeating data

php - 使用按钮获取特定数据 PHP MYSQL MORRIS.JS