算法设计思想——分而治之

分而治之

分而治之是算法设计中的一种方法,它将一个问题分成多个和原问题相似的小问题,递归解决小问题,再将结果合并以解决原来的问题。 应用场景:归并排序、快速排序。

leetcode:374 猜数字大小

/**
 * 解题思路:二分搜索同样具备“分、解、合”的特性。这里我们考虑使用分而治之的思想。
 * 解题步骤:
 *  分:计算中间元素,分割数组。
 *  解:递归的在较大或者较小子数组进行二分搜索。
 */

var guessNumber = function(n) {
    const mainCode = (low, high) => {
        //递归的结束点
        if (low > high) {
            return;
        };

        //获取到中间元素的下标
        const mid = Math.floor((low + high) / 2);
        const res = guess(mid);

        //依次作出判断
        if (res === 0) {
            return mid;
        } else if (res === -1) {
            return mainCode(low, mid - 1);
        } else {
            return mainCode(mid + 1, high);
        }
    }
    return mainCode(1, n);
};

leetcode 226 翻转二叉树

/**
 * 解题思路:
 * (1)先将左右子树互换位置,再将子树互换位置
 * (2)符合“分、解、合”特性
 * 
 * 解题步骤:
 * (1)分:获取左右子树
 * (2)解:递归的翻转左右子树
 * (3)合:将翻转后的左右子树换个位置放到根节点上
 */

 var invertTree = function(root) {
    //如果根节点为空, 直接返回null
    if(!root) {
        return null;
    }

    return {
        //每个根节点的值肯定是保持不变的
        val: root.val,
        //将递归好的右子树放在左边
        left: invertTree(root.right),
        //将递归好的左子树放在右边
        right: invertTree(root.left)
    }

    /**
        时间复杂度:O(n)
        空间复杂度:O(n) 相当于二叉树的深度
     */
};

leetcode 100 相同的树

/**
 * 解题思路:两个相同的树:根节点的值相同、左子树相同、右子树相同
 * 解题步骤:
 * (1)分:获取两个树的左右子树 
 * (2)解:递归的判断两个树的左右子树是否相同
 * (3)合:将上述结果进行合并,如果根节点的值也相同,则两棵树相同
 */

 var isSameTree = function(p, q) {
    //左右子树如果为空,则两棵树相同,返回ture
    if(!p && !q) {
        return true;
    }

    //两棵树的根节点值、左右子树相同
    if(p && q && p.val === q.val && 
        isSameTree(p.left, q.left) &&
        isSameTree(p.right, q.right)
    ) {
        return true;
    }
    return false;

    /**
        时间复杂度:O(n)
        空间复杂度:O(n)
     */
};

leetcode 101 对称二叉树

var isSymmetric = function(root) {
    //如果根节点为空,直接返回true
    if(!root) {
        return true;
    }

    //将对称问题转为镜像问题
    const isMirror = (l, r) => {
        //递归的终点
        if(!l && !r) {
            return true;
        }

        if(l && r && l.val === r.val &&
        isMirror(l.left, r.right) && 
        isMirror(l.right, r.left)) {
            return true;
        }

        //否则返回false
        return false;
    }

    //调用一下
    return isMirror(root.left, root.right);

    /*
        时间复杂度:O(n)
        空间复杂度:O(n)
     */
};
  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值