leetcode-x 的平方根

159 阅读2分钟

一起养成写作习惯!这是我参与「掘金日新计划 · 4 月更文挑战」的第2天,点击查看活动详情

刷了一段时间leetcode,也找回了一些做题的感觉,但是刷到哪儿算哪儿也肯定不行,接下来计划按照专题来刷,每1-3周做1个专题的题目,这样可能可以把1种类型的算法理解的更加透彻。本周先从二分法入手,这个自认为之前也写过不少,看看是否能比较熟练的写出来。

题目描述

给你一个非负整数 x ,计算并返回 x 的 算术平方根 。 由于返回类型是整数,结果只保留 整数部分 ,小数部分将被 舍去 。 注意:不允许使用任何内置指数函数和算符,例如 pow(x, 0.5) 或者 x ** 0.5 。

示例 1: 输入: x = 4 输出: 2

示例 2: 输入: x = 8 输出: 2 解释:8 的算术平方根是 2.82842..., 由于返回类型是整数,小数部分将被舍去。

思路

求平方根,又排除了类似pow的函数,我理解题意就是向让我们采用二分法试根。当然后面看别人题解的一些开脑洞的方法,也挺有意思,特别是“牛顿迭代”,可以帮你再复习一些高中和大学的数学知识,然后感叹一下自己曾经竟然也能看懂这些。

我们还是老老实实先把二分法写了,由于求解整数的平方根,所以我们可以把0作为left初始值,把x本身作为right的初始值。由于题目要求只保留整数部分,而循环到最后的状态,一定是left-right=1,所以我们可以直接返回right。当然,最后演变到这种状态的前提是,没有提前跳出循环,如果存在 mid*mid==x的情况,那么我们直接返回mid即可。

本题还有1个注意点是,mid*mid可能超过int的上限,我们可以采用long来接收这个平方结果。

Java版本代码

class Solution {
    public int mySqrt(int x) {
        int left = 0, right = x;
        while (left <= right) {
            int mid = left + (right - left)/2;
            long midSqar = 1L * mid * mid;
            if (midSqar == x) {
                return mid;
            } else if (midSqar < x) {
                left = mid + 1;
            } else {
                right = mid - 1;
            }
        }
        return right;
    }
}