学习记录:js算法(五十七):二叉树中所有距离为 K 的结点

文章目录

二叉树中所有距离为 K 的结点

给定一个二叉树(具有根结点 root), 一个目标结点 target ,和一个整数值 k ,返回到目标结点 target 距离为 k 的所有结点的值的数组。(可以任意顺序返回)

图一:

bash 复制代码
示例 1:
输入:root = [3,5,1,6,2,0,8,null,null,7,4], target = 5, k = 2
输出:[7,4,1]
解释:所求结点为与目标结点(值为 5)距离为 2 的结点,值分别为 7,4,以及 1

示例 2:
输入: root = [1], target = 1, k = 3
输出: []

我的思路

没有思路,完全不会写
网上思路

递归、栈

网上思路

递归
js 复制代码
var distanceK = function (root, target, k) {
    const parentMap = new Map();

    // 构建父节点映射
    function buildParentMap(node, parent) {
        if (!node) return;
        parentMap.set(node, parent);
        buildParentMap(node.left, node);
        buildParentMap(node.right, node);
    }

    buildParentMap(root, null);

    // 找到目标节点
    let targetNode = null;
    function findTarget(node) {
        if (!node) return;
        if (node === target) {
            targetNode = node;
            return;
        }
        findTarget(node.left);
        findTarget(node.right);
    }

    findTarget(root);

    // BFS 找到距离为 k 的节点
    const result = [];
    const visited = new Set();
    const queue = [[targetNode, 0]]; // [节点, 当前距离]
    visited.add(targetNode);

    while (queue.length > 0) {
        const [currentNode, currentDistance] = queue.shift();

        if (currentDistance === k) {
            result.push(currentNode.val);
        }

        // 遍历子节点
        if (currentNode.left && !visited.has(currentNode.left)) {
            visited.add(currentNode.left);
            queue.push([currentNode.left, currentDistance + 1]);
        }

        if (currentNode.right && !visited.has(currentNode.right)) {
            visited.add(currentNode.right);
            queue.push([currentNode.right, currentDistance + 1]);
        }

        // 遍历父节点
        const parentNode = parentMap.get(currentNode);
        if (parentNode && !visited.has(parentNode)) {
            visited.add(parentNode);
            queue.push([parentNode, currentDistance + 1]);
        }
    }

    return result;
};

讲解
distanceK 函数:

  1. buildParentMap 函数通过 DFS 遍历树,并记录每个节点的父节点。
  2. findTarget 函数找到目标节点。
  3. 使用 BFS 从目标节点开始,记录当前节点的距离,并将距离为 k 的节点值添加到结果数组中。
  4. 返回结果数组。

js 复制代码
var distanceK = function (root, target, k) {
    const parentMap = new Map();
    const stack = [root];

    // DFS to record parent pointers
    while (stack.length) {
        const node = stack.pop();
        if (node.left) {
            parentMap.set(node.left, node);
            stack.push(node.left);
        }
        if (node.right) {
            parentMap.set(node.right, node);
            stack.push(node.right);
        }
    }

    const result = [];
    const visited = new Set();
    const queue = [[target, 0]]; // [node, current distance]

    // BFS to find nodes at distance k
    while (queue.length) {
        const [node, dist] = queue.shift();
        if (visited.has(node)) {
            continue;
        }
        visited.add(node);

        if (dist === k) {
            result.push(node.val);
        }

        // Explore neighbors: left, right, and parent
        if (node.left && !visited.has(node.left)) {
            queue.push([node.left, dist + 1]);
        }
        if (node.right && !visited.has(node.right)) {
            queue.push([node.right, dist + 1]);
        }
        const parent = parentMap.get(node);
        if (parent && !visited.has(parent)) {
            queue.push([parent, dist + 1]);
        }
    }

    return result;
};

讲解
distanceK 函数

  1. 使用一个栈来进行深度优先搜索(DFS),遍历整个树并记录每个节点的父节点。
  2. 使用一个队列进行广度优先搜索(BFS ),从目标节点开始,寻找距离为 k 的节点。
  3. BFS 中,我们检查当前节点的左子节点、右子节点和父节点。
  4. 如果当前距离等于 k,则将节点的值添加到结果数组中。

总结

没有思路,全靠网上的写法

相关推荐
hj5914_前端新手16 分钟前
javascript基础- 函数中 this 指向、call、apply、bind
前端·javascript
Hilaku31 分钟前
都2025年了,我们还有必要为了兼容性,去写那么多polyfill吗?
前端·javascript·css
LuckySusu37 分钟前
【js篇】JavaScript 原型修改 vs 重写:深入理解 constructor的指向问题
前端·javascript
LuckySusu37 分钟前
【js篇】如何准确获取对象自身的属性?hasOwnProperty深度解析
前端·javascript
LuckySusu41 分钟前
【js篇】深入理解 JavaScript 作用域与作用域链
前端·javascript
LuckySusu41 分钟前
【js篇】call() 与 apply()深度对比
前端·javascript
LuckySusu1 小时前
【js篇】addEventListener()方法的参数和使用
前端·javascript
LuckySusu1 小时前
【js篇】深入理解 JavaScript 原型与原型链
前端·javascript
云枫晖1 小时前
手写Promise-构造函数
前端·javascript
naice2 小时前
我对github的图片很不爽了,于是用AI写了一个图片预览插件
前端·javascript·git