[题解]CSP-小明种苹果(续)(线性表)


题目链接.

算法思想

对于整数D而言,意思是发生苹果掉落的苹果树的棵树,注意同一棵苹果树只要掉了一个苹果就得算进去,但是掉了再多也只能算一棵。难点在计算E,好好按照题目给的表达式来计算
在这里插入图片描述
即对于任意一颗树A_i,它以及它的左右相邻两棵都掉落过苹果,就算进去一组。

代码解析

所有树组成一个环,我把它们拉直,成为一条线,用线性表(数组)存起来,为了表示环的特性,特意在一头一尾补充上其相邻的那棵树,巧妙地利用了drop[0], drop[N+1]这两个位置,详细见下面代码。

#include<iostream>
using namespace std;

long long int N, m;
long long int T = 0, D = 0, E = 0;
long long int apple_initial = 0, apple_end = 0, apple = 0;
//apple_initial 初始苹果数,apple_cut 疏果数(cut < 0), apple_end 最后剩余苹果数
int drop[1000005] = { 0 };
int main()
{
	long long int i;
	scanf("%lld", &N);
	for (i = 1; i <= N; i++)
	{
		scanf("%lld", &m);
		//第一个数据为初始苹果数,直接读取
		scanf("%lld", &apple_initial);
		apple_end = apple_initial;
		m--;
		while (m--)	//这样写比用 for 循环省事
		{
			scanf("%lld", &apple);
			if (apple <= 0)	//疏果//记住不要忽略了 apple = 0的情况
			{
				apple_end += apple;
			}
			else  //重新统计     
			{
				if (drop[i] == 0 && apple_end > apple)//有苹果掉落
				{
					D++;		//若它掉落过了,应该只是算一棵
					drop[i] = 1;//记录它掉落了
				}
				apple_end = apple;
			}
		}
		T += apple_end;
	}
	//计算 E
	drop[0] = drop[N];
	drop[N + 1] = drop[1];
	for (i = 1; i <= N; i++)
	{
		if (drop[i-1] && drop[i] && drop[i+1])
		{
			E++;
		}
	}
	printf("%lld %lld %lld", T, D, E);
	return 0;
}

结果分析

得分100分,用时250ms,空间使用2.538MB,时间复杂度为O(N)。

猜你喜欢

转载自blog.csdn.net/weixin_44092088/article/details/109897442