第七屆藍橋杯大賽個人賽省賽C++ A/B組 (第八題 四平方和)

四平方和

四平方和定理,又稱爲拉格朗日定理:

每個正整數都可以表示爲至多4個正整數的平方和。

如果把0包括進去,就正好可以表示爲4個數的平方和。

比如:

5 = 0^2 + 0^2 + 1^2 + 2^2

7 = 1^2 + 1^2 + 1^2 + 2^2

(^符號表示乘方的意思)

對於一個給定的正整數,可能存在多種平方和的表示法。

要求你對4個數排序:

0 <= a <= b <= c <= d

並對所有的可能表示法按 a,b,c,d 爲聯合主鍵升序排列,最後輸出第一個表示法

程序輸入爲一個正整數N (N<5000000)

要求輸出4個非負整數,按從小到大排序,中間用空格分開

例如,輸入:5

則程序應該輸出:0 0 1 2

再例如,輸入:12

則程序應該輸出:0 2 2 2

再例如,輸入:773535

則程序應該輸出:1 1 267 838

資源約定:

峯值內存消耗 < 256M

CPU消耗  < 3000ms

請嚴格按要求輸出,不要畫蛇添足地打印類似:“請您輸入...” 的多餘內容。

所有代碼放在同一個源文件中,調試通過後,拷貝提交該源碼。

注意: main函數需要返回0

注意: 只使用ANSI C/ANSIC++ 標準,不要調用依賴於編譯環境或操作系統的特殊函數。

注意: 所有依賴的函數必須明確地在源文件中 #include <xxx>, 不能通過工程設置而省略常用頭文件。

提交時,注意選擇所期望的編譯器類型。


解題思路:對於這一題首先想到的就是暴力四層for循環,但是太費時,所以直接三層for循環是不會超時的,此外還可以將每一層的循環範圍進一步縮小。。。

代碼如下:

#include <stdio.h>
#include <math.h>
#include <string.h>
#include <algorithm>
using namespace std;

int main()
{
	int n,f=0;
	scanf("%d",&n);
	for(int i=0;i<=(int)sqrt(n/4)+1;i++)
	{
		for(int j=i;j<=(int)sqrt(n/3)+1;j++)
		{
			for(int k=j;k<=(int)sqrt(n/2)+1;k++)
			{
				int t = (int)sqrt(n-i*i-j*j-k*k);
				if(t*t == n-i*i-j*j-k*k)
					{printf("%d %d %d %d\n",i,j,k,t); f=1; break;}
				if(f) break;
			}
			if(f) break;
		}
		if(f) break;
	}
	return 0;
}


因爲沒有數據測試,如有錯誤,還請指出。。。


發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章