LeetCode 367. Valid Perfect Squarehtml
判斷一個正數是不是徹底平方數,不可以使用sqrt函數。c++
這是一道簡單題,可是卻挺有思考價值的。本題有不少種解法,思路各異,能夠都看看。算法
數學裏有一個概念叫作等差數列,徹底平方數剛好是奇數等差數列之和。1+3+5+...+(2n-1)=(1+2n-1)n/2=n^2。既然有了這個,那就好辦了,從小到大依次減去奇數,最後判斷是否等於0便可。時間複雜度爲 \(O(sqrt(n))\)。參考代碼以下:函數
class Solution { public: bool isPerfectSquare(int num) { int x = 1; while (num > 0) { num -= x; x += 2; } return num == 0; } };
從1搜索到sqrt(num),時間複雜度爲 \(O(sqrt(n))\)。參考代碼以下:spa
class Solution { public: bool isPerfectSquare(int num) { for (int i = 1; i <= num / i; ++i) { if (i * i == num) return true; } return false; } };
其實就是搜索一個數,天然能夠想到二分法。時間複雜度 \(O(lg(n))\)。參考代碼以下:code
class Solution { public: bool isPerfectSquare(int num) { long left = 0, right = num; while (left <= right) { long mid = left + (right - left) / 2, t = mid * mid; if (t == num) return true; else if (t < num) left = mid + 1; else right = mid - 1; } return false; } };
萬惡的算法,居然還有一個 \(O(1)\) 的解法,不過很難弄懂。參考連接:O(1) time c++ solution inspired by Q_rsqrt。想弄懂的還能夠參考一下這個概念:Fast Inverse Square Root。htm
代碼大概是這個樣子的,學不來學不來:blog
class Solution { public: bool isPerfectSquare(int num) { if (num < 0) return false; int root = floorSqrt(num); return root * root == num; } int32_t floorSqrt(int32_t x) { double y=x; int64_t i=0x5fe6eb50c7b537a9; y = *(double*)&(i = i-(*(int64_t*)&y)/2); y = y * (3 - x * y * y) * 0.5; y = y * (3 - x * y * y) * 0.5; i = x * y + 1; return i - (i * i > x); } };
LeetCode All in One題解彙總(持續更新中...)ip
本文版權歸做者AlvinZH和博客園全部,歡迎轉載和商用,但未經做者贊成必須保留此段聲明,且在文章頁面明顯位置給出原文鏈接,不然保留追究法律責任的權利.leetcode