题目来源:2023 年 12 月 CCF GESP C++ 二级 编程题 第一题 小杨做题

1 题目:小杨做题

题目描述:
为了准备考试,小杨每天都要做题。
第 1 天,小杨做了 1 道题;第 2 天,小杨做了 2 道题;从第 3 天起,小杨每天做的题目数量是前两天的总和。
此外,小杨还规定,当自己某一天做了大于或等于 m 题时,接下来的所有日子里,他就再也不做题了。
请问,到了第 N 天,小杨总共做了多少题呢?
输入:
总共 4 行。第一行一个整数 a,第二行一个整数 b,第三行一个整数 m,第四行一个整数 N。
保证 0 < = a , b < = 10 0<=a,b<=10 0<=a,b<=10 a , b < M < = 1000000 a,b<M<=1000000 a,b<M<=1000000 3 < = N < = 364 3<=N<=364 3<=N<=364
输出:
一行一个整数,表示小杨 N 天里共做了多少题目。
特别提醒:
在常规程序中,输入、输出时提供提示是好习惯。但在本场考试中,由于系统限定,请不要在输入、输出中附带任何提示信息。
样例输入 1:
1
2
10
5
样例输出 1:
19
样例解释 1:
小杨第一天做 1 题,第二天做 2 题,第三天做 1+2=3 题,第四天做 2+3=5 题,第五天做 3+5=8 题。因此他总共做了 1+2+3+5+8=19 题。
样例输入 2:
1
1
5
8
样例输出 2:
12
样例解释 2:
小杨前 5 天分别做了 1,1,2,3,5 题,由于第 5 天小杨做了 5 题,而 m=5 ,于是小杨从此以后不再做题。因此小杨总共做了 1+1+2+3+5=12 题。

2 题目分析

第一步,完成输入部分,根据要求,输入总共 4 个数。
第 1 个整数 a,第 2 个整数 b,第 3 个整数 m,第 4 个整数 N。
并且所有的数据范围 0 < = a , b < = 10 0<=a,b<=10 0<=a,b<=10 a , b < M < = 1000000 a,b<M<=1000000 a,b<M<=1000000 3 < = N < = 364 3<=N<=364 3<=N<=364 ,都在 int 范围内。

int a,b,m,N;
cin>>a>>b>>m>>N;

输入部分完成!
接下来,分析题目意思,小杨的做题数量为:
第 1 天,做了 1 道题;第 2 天,做了 2 道题;从第 3 天起,每天做的题目数量是前两天的总和。
这个和斐波那契数列非常像,代入输入的变量,转换为:第 1 天,做 a 题,第 2 天,做 b 题,第 3 天,做 a+b 题,第 4 天,做 b+a+b 题,以此类推。
可以得出以下规律:
![[Pasted image 20231220100939.png]]
但是这样的规律看起来太复杂了,可以用一个新的变量来替代第三天。
![[Pasted image 20231220101316.png]]
接着在继续用一个新的变量来代替第四天,以此类推。

int c=a+b;//a代替第一天,b代替第二天,c代替第三天
a=b;//要计算第四天时,第二天,变成第一天
b=c;//第三天,变成第二天

接着要进行 N 天,由于前面两天已经知道,因此循环从第 3 天开始。

for(int i=3;i<=N;i++)
{
}

结合在一起。

for(int i=3;i<=N;i++)
{
	int c=a+b;//a代替第一天,b代替第二天,c代替第三天
	a=b;//要计算第四天时,第二天,变成第一天
	b=c;//第三天,变成第二天
}

完成之后,可以代入数据验证一下,查看结果是否符合要求。

#include<iostream>
using namespace std;
int main()
{
	int a,b,m,N;
	cin>>a>>b>>m>>N; 
	int c=0; 
	for(int i=3;i<=N;i++)
	{
		c=a+b;//a代替第一天,b代替第二天,c代替第三天
		a=b;//要计算第四天时,第二天,变成第一天
		b=c;//第三天,变成第二天
	}
	cout<<c;
	return 0; 
}

可以用样例输入 1 进行验证,发现输出 8,刚好是第 5 天所做的题,因此该写法正确!
![[Pasted image 20231220102446.png]]
但这不是最终答案,要求输出的是总题目数。所以需要一个累加器。

int ans=0;//累加器,初始值为0

但由于循环是从 3 开始,因此需要将前两天的和加入到累加器中。

ans=a+b;

再将累加器放入到循环中,对数据进行累加。

int ans=a+b;
for(int i=3;i<=N;i++)
{
	int c=a+b;//a代替第一天,b代替第二天,c代替第三天
	a=b;//要计算第四天时,第二天,变成第一天
	b=c;//第三天,变成第二天
	ans+=c;//进行累加
}

题目中还有一个限制,就是当小杨某一天做了大于或等于 m 题时,接下来的所有日子里,他就再也不做题了。
所以需要进行限制,即 c 变量遇到大于等于 m 时,跳出整个循环。

int ans=a+b;
for(int i=3;i<=N;i++)
{
	int c=a+b;//a代替第一天,b代替第二天,c代替第三天
	a=b;//要计算第四天时,第二天,变成第一天
	b=c;//第三天,变成第二天
	ans+=c;//进行累加
	if(c>=m) break;
}

以上,即完成整个程序逻辑,最后加上输出即可!

3 参考代码

#include<iostream>
using namespace std;
int main()
{
	int a,b,m,N;
	cin>>a>>b>>m>>N; 
	int ans=a+b;
	for(int i=3;i<=N;i++)
	{
		int c=a+b;//a代替第一天,b代替第二天,c代替第三天
		a=b;//要计算第四天时,第二天,变成第一天
		b=c;//第三天,变成第二天
		ans+=c;//进行累加
		if(c>=m) break;
	}
	cout<<ans;
	return 0; 
}

Logo

开放原子开发者工作坊旨在鼓励更多人参与开源活动,与志同道合的开发者们相互交流开发经验、分享开发心得、获取前沿技术趋势。工作坊有多种形式的开发者活动,如meetup、训练营等,主打技术交流,干货满满,真诚地邀请各位开发者共同参与!

更多推荐