采用二分法进行判断,需要对零进行排除,因为为了防止溢出,我采取的是compare(x/a,a)的方式,如果a==0,那么比较将无意义,
时间复杂度为O(logn)
空间复杂度为O(1)
public int mySqrt(int x) {
if(x==0)return 0;
//采用二分法,左节点和右节点
int left=1;
int right=x;
while(left<right){
// 注意:这里一定取右中位数,如果取左中位数,代码会进入死循环,我取的左中位数,但是要对x进行mid+1的操作,还需要对其进行后处理
int mid=(left+right)>>1;
if(x/mid>mid){
left=mid+1;
}else if(x/mid==mid){
return mid;
}else{
right=mid-1;
}
}
//如果left*left>x,则减1,主要是对left=mid+1的补救
if(x/left<left){
left--;
}
return left;
}
while (left < right) {
// 注意:这里一定取右中位数,如果取左中位数,代码会进入死循环
// long mid = left + (right - left + 1) / 2;
long mid = (left + right + 1) >>> 1;
long square = mid * mid;
if (square > x) {
right = mid - 1;
} else {
left = mid;
}
}
作者:liweiwei1419
链接:https://leetcode-cn.com/problems/sqrtx/solution/er-fen-cha-zhao-niu-dun-fa-python-dai-ma-by-liweiw/
来源:力扣(LeetCode)
著作权归作者所有。商业转载请联系作者获得授权,非商业转载请注明出处。
相似题目
这道题和69最大的区别就是 趋向于和等于的区别
当x/a=a时,他的平方根一定是a,但是不一定是完全平方根 x 5 a 2
所以我们需要对它在进一步判别
public boolean isPerfectSquare(int num) {
if(num==1)return true;
int left=1;
int right=num;
while(left<right){
int mid=(left+right+1)>>1;
if(num/mid>mid){
left=mid;
}else if(num/mid==mid){
if(mid*mid==num)
return true;
else
left=mid;
}else{
right=mid-1;
}
}
return false;
}