[Leetcode]279.完全平方数
2018-12-31 16:10
441 查看
最开始的时候,我想到的动态方程很简单,就是
dp[i]=min(dp[i],dp[i-平方数]+1)
其中
i-平方数一定要大于0要不然就会越界。这个思路很简单,举个例子:
dp[5]=min(dp[5-1^2]+1,dp[5-2^2]+1,dp[5])
这表示5可以如下组合:
dp[5] = min(所有组成4的完全平方数+完全平方数1即dp[4]+1, 所有组成1的平方数+完全平方数4即dp[1]+1)
这个方程在初始化dp[0] ,dp[1],dp[2] 和其他的dp为一个大值之后就非常简单了,只需往
MAXN迭代就行了,算法的效率为O(nlog n)
原始解法:
class Solution { public: int numSquares(int n) { const int MAXN=10000; int dp[MAXN+1]; memset(dp,0x3f3f3f3f,sizeof(dp)); dp[0]=0; dp[1]=1; /*1*1=1*/ dp[2]=2; /*1*1+1*1=2*/ dp[3]=3; /*1*1+1*1+1*1=3*/ dp[4]=1; /*2*2=4*/ for(int i=5;i<=MAXN;i++){ for(int j=1;i-j*j>=0;j+=1){ dp[i]=min(dp[i],dp[i-j*j]+1); } } return dp ; } };
这个算法虽然非常容易实现但效率非常的低,我们依然尝试这个方程,换一个方向去实现。
这次使用了
vector来存储
dp数组,目的是为了节省空间。在第二层遍历的时候
for (int j=1; i+j*j <= n; j++)
我们通过正向进行遍历算法方便理解。
代码在执行上比原来的代码要快,但是还是没有改变算法的O(nlog n)的效率
class Solution { public: const int MAXN=0x3f3f3f3f; int numSquares(int n) { vector<int> dp(n+1, MAXN); dp[0] = 0; for (int i=0; i<=n; i++) for (int j=1; i+j*j <= n; j++) { dp[i+j*j] = min(dp[i+j*j], dp[i] + 1); } return dp.back(); } };
我们看一下最高效的解法,这种解法没有用到动态规划而是用数学的方法解决的。我们枚举答案后发现每一个正数必由1-4个完全平方数,没有超过4。这在数学上又叫做[四平方定理][https://baike.baidu.com/item/%E5%9B%9B%E5%B9%B3%E6%96%B9%E5%92%8C%E5%AE%9A%E7%90%86]
即满足四数平方和定理的数n(一定由四个数构成),必定满足n=4^a(8b+7)
这样我们可以通过定理快速写出如下代码。
class Solution { public: int numSquares(int n) { // 去除4因子 while (n % 4 == 0) n /= 4; // 若除8余7,满足四平方定理,必由4个完全平方数组成 if (n % 8 == 7) return 4; // 再尝试将其拆成两个或一个完全平方数 for (int i=0; i*i <= n; i++) { int b = sqrt(n - i*i); if (i*i + b*b == n) return !!i + !!b; } return 3; } };
相关文章推荐
- leetcode279 Perfect Squares(完全平方数)
- 从 LeetCode 279 实践动态规划
- Leetcode #279 Perfect Squares
- [leetcode 279]Perfect Squares
- [LeetCode] Perfect Squares 完全平方数
- 279. 完全平方数
- leetcode刷题,总结,记录,备忘, 279
- LeetCode 279 Perfect Squares 题解
- Leetcode 279 Perfect Squares
- LeetCode 279 PerfectSquares
- [LeetCode] Valid Perfect Square 检验完全平方数
- [leetcode] 279 Perfect Squares(DP,四平方和定理)
- LeetCode 2016.3.8 313,264,95,224,279,275,274
- leetcode谷歌面试题279. Perfect Squares
- leetcode279:Perfect Squares
- (LeetCode 279) Perfect Squares
- [LeetCode#279] Perfect Squares
- LeetCode279——Perfect Squares
- 279.完全平方数-python.md
- LeetCode 279 Perfect Squares