目录
第1关:求和
题目:
代码思路:
代码表示:
第2关:回文数计算
题目:
代码思路:
代码表示:
第3关: 编写函数求表达式的值
题目:
代码思路:
代码表示:
第4关:阶乘数列:
题目:
代码思路:
代码表示:
第5关:亲密数:
题目:
代码思路:
代码表示:
第6关:公约公倍数:
题目:
代码思路:
代码表示:
第1关:求和
题目:
题目描述:给你一个
n
,要求你编写一个函数求1+2+.......+n.
输入一个
n
输出
1+2+.......+n
的和样例输入:
100
样例输出:
5050
代码思路:
这题只需要创建一个有for循环的函数,将n~1的数相加即可
代码表示:
#include<stdio.h>
//编写函数
/*********Begin*********/
int a(int n)
{
int sum=0;
for(int i =1;i<=n;i++)
{
sum += i;
}
return sum;
}
/*********End**********/
int main(void)
{
/*********Begin*********/
int n,sum;
scanf("%d",&n);
sum=a(n);
printf("%d",sum);
/*********End**********/
return 0;
}
第2关:回文数计算
题目:
本关任务:编写函数求区间
[200,3000]
中所有的回文数,回文数是正读和反读都是一样的数。如525
,1551
输出区间
[200,3000]
中所有的回文数,一行一个回文数,不需要输出其它无关的字符。
202
212
222
232
242
.....
代码思路:
本题的难点在于回文数的判断,我的想法是通过%求出原数k的每一位,然后将其*10重新组合,重新组合后的数如果与前面的数相等,那就是回文数
代码表示:
#include<stdio.h>
void solve()
{
/*********Begin*********/
int i, k, t;
for (i = 200; i <= 3000; i++)
{
k = i, t = 0;
while (k)
{
t *= 10;
t += k % 10;
k /= 10;
}
if (t == i)
printf("%d\n", i);
}
/*********End**********/
}
int main(void)
{
solve();
return 0;
}
第3关: 编写函数求表达式的值
题目:
题目描述:有如下表达式
s = 1 + 1 / 3 + (1 * 2) / (3 * 5) + (1 * 2 * 3) / (3 * 5 * 7) + .... + (1 * 2 * 3 * .... * n) / (3 * 5 * 7 * ... * (2 * n + 1))
。编写函数求给出的n所对应的表达式s的值。
样例输入:
4
样例输出:
1.5492063492
代码思路:
这题的难点在于将不断变化的分子分母表示出来,我用的是循环的方法,分子用for循环每次加1,分母每次加2,然后将其累乘
代码表示:
#include<stdio.h>
//编写题目要求的函数
/*********Begin*********/
double sum(int n)
{
double sum = 1, t1 = 1, t2 = 1, a = 1;
int i;
for (i = 1; i <= n; i++)
{
t1 *= i;
t2 *= (a += 2);
sum += t1 / t2;
}
}
/*********End**********/
int main(void)
{
/*********Begin*********/
int n;
scanf("%d", &n);
printf("%.10f\n", sum(n));
/*********End**********/
return 0;
}
第4关:阶乘数列:
题目:
题目描述:求
Sn=1!+2!+3!+4!+5!+…+n!
之值,其中n
是一个数字。样例输入:
5
样例输出:
153
提示:
用
int
可能会溢出,需要用能表示更大范围的long long
int
(注:VC6.0
不支持此类型,VC
下使用可使用__int64
替代)
代码思路:
这题的难点在于如何表示阶乘,我这里采用for循环,先用1*1表示1的阶乘,然后第一次循环后就是1*2表示2的阶乘,第二次循环就是1*2的值*3表示3的阶乘.....每一次循环都有sum += t使每一次的阶乘可以相加
代码表示:
#include<stdio.h>
long long sum(int n)
{
long long sum = 0, t = 1;
int i;
for (i = 1; i <= n; i++)
{
t *= i;
sum += t;
}
return sum;
}
/*********End**********/
int main(void)
{
/*********Begin*********/
int n;
scanf("%d", &n);
printf("%lld\n", sum(n));
/*********End**********/
return 0;
}
第5关:亲密数:
题目:
题目描述:两个不同的自然数
A
和B
,如果整数A
的全部因子(包括1
,不包括A
本身)之和等于B
;且整数B的全部因子(包括1
,不包括B
本身)之和等于A
,则将整数A
和B
称为亲密数。求3000
以内的全部亲密数。样例输出:
(220,284)(1184,1210)(2620,2924)
提示:
按照亲密数定义,要判断数a是否有亲密数,只要计算出a的全部因子的累加和为
b
,再计算b
的全部因子的累加和为n
,若n
等于a
则可判定a
和b
是亲密数。计算数a
的各因子的算法:用a依次对
i(i=1~a/2)
进行模运算,若模运算结果等于0
,则i
为a
的一个因子;否则i就不是a
的因子。
代码思路:
本题的难点在于如何得到因子相加,我的思路就是用for循环的方式,如果n%i==0,说明 i 是 n 的因子,然后将其相加即可。注意在写代码时不能忽略 a<b 这个细节
代码表示:
int getSum(int n)
{
int sum = 0, i;
for (i = 1; i < n; i++)
{
if (n % i == 0)
sum += i;
}
return sum;
}
void solve()
{
/*********Begin*********/
int a, b;
for (a = 2; a <= 3000; a++)
{
b = getSum(a);
if (a == getSum(b) && a < b)
printf("(%d,%d)", a, b);
}
/*********End**********/
}
int main(void)
{
solve();
return 0;
}
第6关:公约公倍数:
题目:
题目描述:写两个函数,分别求两个整数的最大公约数和最小公倍数,用主函数调用这两个函数,并输出结果。两个整数由键盘输入。
样例输入:
6 15
样例输出:
3 30
提示:
- 负数没有最大公约数和最小公倍数;
- 最大公约数和最小公倍数一定为正数,不可以为负数;
- 需要考虑代码运行效率,否则会评测超时。
代码思路:
最大公因数求法:
辗转相除法:也叫欧几里得算法,是求最大公因数最常用的方法。假设需要求出整数a和b的最大公因数,我们用a除以b得到余数c,然后将b赋值为a,将c赋值为b,重复这个过程直到余数为0,此时的b就是a和b的最大公因数。例如,求出84和36的最大公因数:首先84除以36得到余数12,于是将36赋值为84,将12赋值为36,继续进行36除以12得到余数0,此时的36就是84和36的最大公因数。
最小公倍数求法:
两个数的乘积等于这两个数的最大公约数与最小公倍数的乘积。假设有两个数是a、b,它们的最大公约数是p,最小公倍数是q。那么有这样的关系:ab=pq。
代码表示:
#include<stdio.h>
//编写最大公约数GCD函数
/*********Begin*********/
long long gcd(long long n, long long m)
{
int t, r;
if (n > m)
{
t = n; n = m; m = t;
}
while ((r = m % n) != 0)
{
m = n;
n = r;
}
return(n);
}
/*********End**********/
//编写最小公倍数LCM函数
/*********Begin*********/
long long lcm(long long n, long long m)
{
return n / gcd(n, m) * m;
}
/*********End**********/
int main()
{
/*********Begin*********/
long long n, m;
scanf("%lld%lld", &n, &m);
if (n < 0 || m < 0)
printf("Input Error\n");
else
printf("%lld %lld\n", gcd(n, m), lcm(n, m));
/*********End**********/
return 0;
}