青岛市程序设计竞赛冲刺②

2022青岛市小学组第三题

原题:

 

 

 

 

 

 代码:

#include<bits/stdc++.h>
#define ll long long
using namespace std;
ll n,ans=0,t;
int main(){
	freopen("turn.in","r",stdin);
	freopen("turn.out","w",stdout);
	cin>>n;t=sqrt(n);
	if(n==2)cout<<0;
	else if(t*t!=n)cout<<-1;
	else{
		ans=n-2+1;
		while(t!=2){
			ll tmp=(t-1)*(t-1);
			ans+=tmp-t+1;
			t--;
		}
		cout<<ans;
	}
	return 0;
}

  

 

解题思路:

分三种情况,第一种,n=2,直接输出0

      第二种,sqrt(n)2≠n,直接输出-1

      第三种,sqrt(n)2=n,这个数会每次先遍历到n,从n开方,遍历到(sqrt(n)-1),从(sqrt(n)-1)2开方,重复执行这种操作,直至开方结果等于2,累计次数即为答案

也可以用平方和的通项公式,n(n+1)(2n+1)/6

#include<cstdio>
#include<iostream>
#include<cmath>
using namespace std;
long long n,p;
int main(){
    scanf("%lld",&n);
    if(n==2){
        printf("0\n");
        return 0;
    }
    long long t=sqrt(n);
    if(t*t!=n)printf("-1\n");
    else{
        long long ans=n-2+t-1;
        p = t - 1;
        ans = ans + (p * (p + 1) * (2 * p + 1) / 6 - 1)-(p*(p+1)/2-1)-(t-2);
        printf("%lld\n",ans);
    }
    return 0;
}

  

也可以提前算出平方数,求和

#include<bits/stdc++.h>
#define MX 1000000
typedef long long int LL;
using namespace std;
LL n,a[MX + 10] = {0,0};
LL i,ans,x,p,k = 1;

int main()
{

    for(i = 2; i * i <= 1e12; i++)
    {
        a[++k] = i * i;
    }
    scanf("%lld",&n);
    p = sqrt(n);
    if(n == 2)
    {
        ans = 0;
    }
    else if(p * p != n)
    {
        ans = -1;
    }
    else
    {
        x = lower_bound(a + 1,a + k + 1,n) - a;
        p = 2;
        do
        {
            ans = ans + (a[x] - p) + 1;
            p = x;
            x--;
        }
        while(x >= 2);
    }
    cout << ans << endl;
    return 0;
}

  

 

posted @ 2023-04-22 21:56  天雷小兔  阅读(67)  评论(0)    收藏  举报