MySQL WITH RECURSIVE在PHP中无法运行的问题求助
问题根源
你的MySQL服务器版本是5.7.30,该版本不支持递归CTE(WITH RECURSIVE语法)——递归CTE是从MySQL 8.0才正式引入的特性。dbfiddle默认使用的是MySQL 8.0+环境,所以语句能正常运行,但PHP连接的5.7服务器会因语法不兼容报错。
解决办法
如果无法升级MySQL版本,可通过以下两种方式替代递归CTE实现层级分类输出:
方案1:数据库自定义函数(递归查询层级)
创建一个自定义函数,传入分类ID后递归拼接层级路径:
DELIMITER // CREATE FUNCTION getCategoryHierarchy(category_id INT) RETURNS VARCHAR(500) DETERMINISTIC BEGIN DECLARE full_path VARCHAR(500); DECLARE current_parent INT; SET full_path = CAST(category_id AS CHAR); SELECT parent_id INTO current_parent FROM categories WHERE id = category_id; WHILE current_parent IS NOT NULL AND current_parent != 0 DO SET full_path = CONCAT(current_parent, ' > ', full_path); SELECT parent_id INTO current_parent FROM categories WHERE id = current_parent; END WHILE; RETURN full_path; END // DELIMITER ;
查询时调用函数即可获取层级信息:
SELECT id, name, getCategoryHierarchy(id) AS hierarchy FROM categories;
方案2:PHP端构建树形结构后遍历
先一次性查询所有分类数据,在PHP中构建树形结构,再递归遍历输出层级:
// 连接数据库并查询所有分类 $pdo = new PDO('mysql:host=你的主机;dbname=你的库名;charset=utf8', '用户名', '密码'); $stmt = $pdo->query("SELECT id, name, parent_id FROM categories"); $allCats = $stmt->fetchAll(PDO::FETCH_ASSOC); // 构建分类树形结构 $catTree = []; foreach ($allCats as $cat) { $catTree[$cat['id']] = $cat + ['children' => []]; } foreach ($allCats as $cat) { if ($cat['parent_id'] != 0 && isset($catTree[$cat['parent_id']])) { $catTree[$cat['parent_id']]['children'][] = &$catTree[$cat['id']]; } } // 递归遍历输出层级(可调整为从底到顶逻辑) function outputHierarchy($cats, $level = 0) { foreach ($cats as $cat) { echo str_repeat(' ', $level) . $cat['name'] . "\n"; if (!empty($cat['children'])) { outputHierarchy($cat['children'], $level + 1); } } } // 输出所有顶级分类(parent_id=0)的层级 $topCats = array_filter($catTree, fn($cat) => $cat['parent_id'] == 0); outputHierarchy($topCats);
额外说明
如果业务允许,直接升级MySQL服务器到8.0及以上版本,即可直接使用原递归CTE语句,无需修改代码。
内容的提问来源于stack exchange,提问作者Andrealuigi
相关产品推荐
相关产品推荐

