前端学算法^-^

10.17(滑动窗口 sliding window(技巧) 209/1456)

时间复杂度不要看是两个循环嵌套就认为是O(n^2),看元素的操作次数,元素在right移动时进来一次,left移动时出去一次所以是2n次,时间复杂度O(n)。

var minSubArrayLen = function(target, nums) {
    // 长度计算一次
    const len = nums.length;
    let l = r = sum = 0,
        res = len + 1; // 子数组最大不会超过自身
    while(r < len) {
        sum += nums[r++];
        // 窗口滑动
        while(sum >= target) {
            // r始终为开区间 [l, r)
            res = res < r - l ? res : r - l;
            sum-=nums[l++];
        }
    }
    return res > len ? 0 : res;
};
10.19递归 recursion 509/206/344/687

// // 普通递归
// var fib = function(n) {
//     if(n==0) return 0;
//     if(n==1) return 1;
//     return fib(n-1)+fib(n-2)

// };

// 递归记忆(因为太递归调用的过程会遇到重复计算,例如meno[10]=meno[9]+meno[8],而在计算meno[9]的时候又需要计算meno[8],所以可以用一个数组把计算过的储存起来。
var fib =function(n) {
    let meno =new Array(n+1).fill(0);
    let dfs =(n) =>{
        if(n==0) {
            return 0
        }
        if(n==1) {
            return 1
        }
        if(meno[n]) {
            return meno[n]
        }
        meno[n] = dfs(n-1)+dfs(n-2)
        return meno[n];
    }
    return dfs(n)
}

// 递归写法
var reverseList =function(head) {
    // 递归终止条件
    if(head==null||head.next==null) return head
    const p = reverseList(head.next)
    head.next.next = head
    head.next = null
    return p
}

var reverseString = function(s) {
    const helper =(curr)=>{
        // 当curr到达字符串的中间位置(half)时,停止递归
        if(curr==half) {
            return
        }
        // 交换curr和对应位置的字符,实现字符串反转
        [s[curr],s[len-curr-1]]=[s[len -curr-1],s[curr]]
        // 递归调用helper,将curr增加1
        helper(curr+1)
    }
    let len =s.length
    let half=Math.floor(len>>1)
    helper(0)
}

const longestUnivaluePath = (root) => {
    let res = 0; // 用于存储最长相同值路径的长度

    const dfs = (root) => {
        if (root == null) {
            return 0; // 如果节点为空,返回 0
        }
        const left = dfs(root.left); // 递归计算左子树的路径长度
        const right = dfs(root.right); // 递归计算右子树的路径长度

        let leftPath = 0, rightPath = 0;

        if (root.left && root.left.val == root.val) {
            leftPath = left + 1; // 如果左子节点的值与当前节点相同,更新左子树路径长度
        }
        if (root.right && root.right.val == root.val) {
            rightPath = right + 1; // 如果右子节点的值与当前节点相同,更新右子树路径长度
        }
        res = Math.max(res, leftPath + rightPath); // 更新最长相同值路径长度

        return Math.max(rightPath, leftPath); // 返回当前节点的最长相同值路径长度
    }

    dfs(root); // 调用递归函数
    return res; // 返回最长相同值路径长度
}

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值