完全平方数【Letcode279题解】

完全平方数

这道题目是一道很好的题目,下面写两个题解 DP 和 数学的

动态规划

个人理解动态规划是这样的:把 fi 用 fj (j<i)相关的式子进行表示,那么我们就要想着去找一个比 i 小的 j 来构造 fi

再审视一下这道题目,我们要用完全平方数的和来表示这个数字 i i i,那么我们可以考虑到(假设)这个 i i i 有一个 完全平方数 j 2 j^2 j2 作为一部分那么我们可以写出这样的式子 i = j 2 + ( i − j 2 ) i=j^2+(i-j^2) i=j2+(i−j2)

于是乎我们就可以知道 fi = 1+ fi-j\*j 了这就是这道题目的动态转移方程,具体CPP代码如下

cpp 复制代码
#include<iostream>
#include<vector>
using namespace std;

int numSquares(int n){
	vector<int> msq(n+1);
	// 不考虑 0 
	for(int i=1;i<=n;i+=1){
		int t=i;
		for(int j=1;j*j<=i;j+=1){
			t=min(t,msq[i-j*j]);
		}
		msq[i]=1+t;
	}
	return msq[n];
}

int main(){
	int n;
	cin>>n;
	cout<<numSquares(n);
	return 0;
}

拉格朗日四平方和定理

借用了letcode题解的思路

如果你数学好一点,就知道 四平方定理 这个概念:四平方和定理_百度百科

由拉格朗日证明的:每一个正整数 n 都可以表示为 4 个整数的平方和,即一定存在
x = x 1 2 + x 2 2 + x 3 2 + x 4 2 x = x_1^2+x_2^2+x_3^2+x_4^2 x=x12+x22+x32+x42

根据这个定理我们就可以知道当 n = 4 k ∗ ( 8 m + 7 ) n = 4^k * (8m+7) n=4k∗(8m+7) 的时候,n只能被4个整数的平方和表示,那么接下来的情况就剩下 1,2,3个了

当 res =1的时候 n 本身就是一个完全平方数,当 res = 2 的时候可以枚举这两个整数,当res 不等于 1,2,4的时候 res 一定等于 3,由此可以得到结果

具体的Cpp语言解法如下:

cpp 复制代码
#include<iostream>
#include<cmath>
using namespace std;

bool isPerfectSquare(int n){
	int t=sqrt(n);
	return t*t==n;
}

bool isfour(int n){
	while(n%4==0){
		n/=4;
	}
	return  n%8==7;
}

int numSquare(int n){
	if(isPerfectSquare(n)){
		return 1;
	}
	if(isfour(n)){
		return 4;
	}
	for(int i=1;i*i<n;i+=1){
		int j=n-i*i;
		if(isPerfectSquare(j)){
			return 2;
		}
	}
	return 3;
}

int main(){
	int n;
	cin>>n;
	cout<<numSquare(n);
	return 0;
}
相关推荐
聪明的笨猪猪5 分钟前
AI应用架构选型:架构师的核心决策困境与权衡
经验分享·面试·架构
波力海苔夹心脆67517 分钟前
C# WPF 资源字典详解:ResourceDictionary、MergedDictionaries 与自定义控件案例
开发语言·c#·wpf·入门教程·resource·资源字典
不会算法的笨小孩39 分钟前
异常的使用以及会出现的问题
开发语言·c++·c++11·异常
LabVIEW开发1 小时前
LabVIEW 连接板:28 个端子怎么排,优先级怎么定
java·算法·labview
疯华整猫2 小时前
被杀掉之后:我把 Android 的「唤起 + 常驻」重做了一遍
前端·面试·架构
严肃小白兔2 小时前
MATLAB 数值计算中的精度与误差问题:浮点运算、误差传播与数值稳定性
人工智能·算法·matlab
nice_lcj5202 小时前
Java 并发容器入门:ConcurrentHashMap、CopyOnWriteArrayList、阻塞队列
java·面试·并发编程·阻塞队列·concurrenthashmap·copyonwritearraylist
Hhy_11073 小时前
《C++深度解构06》手撕 string —— 从底层内存管理到深浅拷贝彻底吃透
c语言·开发语言·c++·学习·visual studio
starzy19903 小时前
深入理解Scala函数定义:从方法到函数的类型跨越
开发语言·scala
starzy19903 小时前
深入理解Scala递归函数:从栈溢出到尾调用优化
开发语言·scala