赞
踩
本题要求统计给定整数M和N区间内素数的个数并对它们求和。
输入在一行中给出两个正整数M和N(1≤M≤N≤500)。
在一行中顺序输出M和N区间内素数的个数以及它们的和,数字间以空格分隔。
10 31
7 143
#include<stdio.h> #include<math.h> int prime(int x); int main(){ int M,N; scanf("%d %d", &M,&N); int count=0,sum=0; for (int i=M;i<=N;i++){ if (prime(i)){ sum += i; count++; } } printf("%d %d", count,sum); return 0; } int prime(int x){ if (x==1) return 0; for (int i=2; i<=sqrt(x); i++) if (x%i==0) return 0; return 1; }
整个程序的编写思路为:
在上一篇关于输入输出的内容里,有提到过关于基本框架的事情,在此对基本框架的内容进行一些完善,具体如下:
#include <stdio.h>
int main()
{
int M, N; //定义需要用到的变量
int count = 0, sum = 0; //变量的初始化
scanf("%d %d", &M, &N); //需要输入的变量
/*函数的主体*/
printf("%d %d", count, sum); //需要输出的变量
return 0;
}
对于大多数的问题都有着自己的输入和输出。因此我们在搭建函数框架的时候,可以先将输入和输出的部分全部搞好,剩下我们只用关心变量之间的运算即可。
for
】类似这种已知起点
和终点
要找出在起点和终点之间满足某些规律的数,用for
循环是一种比较简单的方法,使用方式为:for(exp1;exp2;exp3)
后加Loopbody
,其中:
exp1
用于给Loopbody
中的变量赋予初值exp2
用于判定是否执行Loopbody
的语句【非0时执行】exp3
用于在每次执行Loopbody
之后修改变量的值Loopbody
为每次循环中需要执行的语句以遍历M到N之间所有的数为例,具体使用方法如下:
#include <stdio.h> int main() { int M, N; int count = 0, sum = 0; scanf("%d %d", &M, &N); int i; //定义循环变量i for (i = M; i <= N; i++){ /*这里边的内容被称为Loopbody*/ } //也可以在for循环中定义变量,如:for (int i = M; i <= N; i++) printf("%d %d", count, sum); return 0; }
其中:
i = M
:表示i
从M
开始i <= N
:表示在i <= N
的时候执行Loopbody
的内容i++
:表明每次执行完Loopbody
的内容后执行语句i++
这样可以保证i
取到从M
到N
的所有的值
if
】在编写程序的过程中,我们常常需要达到类似“如果xxx”,“就xxx”的效果。而if
函数可以实现这样的效果。if
函数的使用方法为:if(exp)
后加sentence
,其中:
exp
表示判定sentence
是否运行的语句【0
不运行,非0
运行】sentence
表示如果exp
为真需要执行的语句在此题中,我们需要对所有的i
进行判定,判断这个i
是否为素数,具体代码如下:
#include <stdio.h> int main() { int M, N; int count = 0, sum = 0; scanf("%d %d", &M, &N); int i; for (i = M; i <= N; i++){ //利用if判定那个数(i)是否是质数 if (prime(i)){ //如果i是质数prime(i)=1,否则prime(i)=0 /*这里输入stence*/ } } printf("%d %d", count, sum); return 0; }
由于C语言内置的函数中并不包括prime
,所以我们需要自己编写和调用prime
函数。在调用函数之前,我们需要先定义和声明函数,具体方法为
函数类型 函数名称( 变量类型 变量名称)
后接函数体
函数类型 函数名称( 变量类型 变量名称);
在使用前声明以prime
函数为例,具体代码如下:
#include <stdio.h> int prime(int x); //prime函数的声明 int main() { int M, N; int count = 0, sum = 0; scanf("%d %d", &M, &N); int i; for (i = M; i <= N; i++){ if (prime(i)){ /*这里输入sentence*/ } } printf("%d %d", count, sum); return 0; } int prime(int x) //prime函数的定义 { /*这里输入函数体*/ }
prime
函数只能是0或者1,所以函数类型为int
prime
函数的作用是判断一个自然数x
是否为质数,所以输入的参数类型为int
prime
】注:1既不是素数也不是合数
因此编写的思路为:判断一个数x
是否是质数,只需要对从2
到x-1
的所有的数取余数%
,如果存在余数为0
的情况,则说明x
不是质数。【稍微优化一下可以只对2
到sqrt(x)
取余数即可】
为什么是
x
\sqrt{x}
x
证明如下:
若
x
x
x不是质数,也就是说
∀
m
,
n
→
x
=
m
×
n
\forall m,n \rightarrow x = m \times n
∀m,n→x=m×n
且假设
m
≤
n
m\leq n
m≤n:两个数,总有一个小于等于另外一个,则必有:
m
≤
x
≤
n
m \leq \sqrt{x} \leq n
m≤x
≤n
反证法可知,若
m
,
n
<
x
m,n < \sqrt{x}
m,n<x
, 那么
m
×
n
<
x
m \times n < x
m×n<x【大于同理】
故,如果
x
x
x不是质数,那么必定存在一个
x
x
x的因数
m
≤
x
m \leq \sqrt{x}
m≤x
根据上述原理我们可以编写如下程序:
int prime(int x){ //质数判定函数
if (x==1) //如果x为1,那么x不是质数,返回0
return 0;
//如果x大于等于2,开始遍历
for (int i=2; i<=sqrt(x); i++) //从2到sqrt(x) 上边解释了
if (x%i==0) //如果存在余数为0的情况
return 0; //返回0
return 1; //如果运行完所有的都不存在,则返回1
}
统计满足某些条件的数的个数,以及对某些数进行累加,是C程序中很常见的小技巧。通常我们让求和的结果为sum
,用count
来记录个数。
只需要在满足条件的语句(即if
后的sentence
)中增加:
sum += i;
表示每当满足条件的时候sum
再原本的基础上加上i
count++;
表示每当满足条件的时候count
的值增加1在题目中具体的代码样例如下:
#include<stdio.h> #include<math.h> //当使用sqrt函数的需要调用<math.h> int prime(int x); int main(){ int M,N; scanf("%d %d", &M,&N); int count=0,sum=0; for (int i=M;i<=N;i++){ if (prime(i)){ //如果i是素数 sum += i; //sum在原本的值上+i count++; //count的数量+1 } } printf("%d %d", count,sum); return 0; } int prime(int x){ if (x==1) return 0; for (int i=2; i<=sqrt(x); i++) if (x%i==0) return 0; return 1; }
Copyright © 2003-2013 www.wpsshop.cn 版权所有,并保留所有权利。