「csp模拟试题 201909-2」小明种苹果(续)C/C++ 100分

10 篇文章 0 订阅
10 篇文章 0 订阅

目录

  • 题目
  • 输入输出样例
  • 题解思路
  • 题解源码(c/c++)

题目 :小明种苹果(续)

【问题描述】

小明在他的果园里种了一些苹果树,这些苹果树排列成-一个圆。为了保证苹果的品.质,在种植过程中要进行疏果操作。为了更及时地完成疏果操作,小明会不时地检查每棵树的状态,根据需要进行疏果。检查时,如果发现可能有苹果从树上掉落,小明会重新统计树上的苹果个数(然后根据之前的记录就可以判断是否有苹果掉落了)。在全部操作结束后,请帮助小明统计相关的信息。

【输入格式】

从标准输入读入数据。

第 1 行包含一个正整数 N,表示苹果树的棵数。

第 1+i 行(1≤i≤N),每行的格式为 mi, ai,…m…其中,第一个正整数 mi;表示本行后面的整数个数。后续的 mi 个整数表示小明对第 i 棵苹果树的操作记录。若 aj(1≤j≤mi)为正整数,则表示小明进行了重新统计该棵树上的苹果个数的操作,统计的苹果个数为 aij;若为零或负整数,则表示一次疏果操作,去掉的苹果个数是|aij|。

输入保证一定是正确的,满足:

  1. ai1> 0,即对于每棵树的记录,第一个操作一定是统计苹果个数(初始状态,此时不用判断是否有苹果掉落);

  2. 每次疏果操作保证操作后树上的苹果个数仍为正。

【输出格式】

输出到标准输出。

输出只有一行,包含三个整数 T、D、E。其中,

  • T 为全部疏果操作结束后所有苹果树上剩下的苹果总数(假设每棵苹果树在最后一次统计苹果个数操作后苹果不会因为疏果以外的原因减少);

  • D 为发生苹果掉落的苹果树的棵数:

  • E 为相邻连续三棵树发生苹果掉落情况的组数。

对于第三个统计量的解释: N 棵苹果树 A1,A2,…An 排列成一个圆,那么 A1 与 A2 相邻,A2 与 A3 相邻,… AN-1 与 AN 相邻,AN 与 A1 相邻。如果 Ai-1,Ai,Ai+1 这三棵树都发生了苹果掉落的情况,则记为一组。形式化的,有

E = |{Ai|Drop(Pred(Ai)) ^ Drop(Ai) ^ Drop(Succ(Ai))|.

其中,Drop(A)表示苹果树 Ai 是否发生苹果掉落的情况,Pred(Ai) 表示 Ai 的前一棵树 Ai-1 (如果 i> 1)或者 AN (如果 i = 1), Succ(Ai) 表示 Ai 的后一棵树 A+1 (如果 i < N)或者 A1 (如果 i = N)。

输入输出样例

  • 输入样例1
4
4 74 -7 -12 -5
5 73 -8 -6 59 -4
5 76 -5 -10 60 -2
5 80 -6 -15 59 0
  • 输出样例1
222 1 0
样例 1 解释

全部操作结束后,第 1 棵树.上剩下的苹果个数为 74-7-12-5=50,第 2 棵为 59-4=55,第 3 棵为 60-2=58,第 4 棵为 59-0= 59。因此 T = 50+55+58+59 = 222。

其中,第 3 棵树在第 2 次统计之前剩下的苹果个数为 76-5- 10=61> 60,因此发生了苹果掉落的情况。可以检验其他的树没有这种情况,因此 D= 1。

没有连续三棵树都发生苹果掉落的情况,因此 E= 0。

  • 输入样例2
5
4 10 0 9 0
4 10 -2 7 0
2 10 0
4 10 -3 5 0
4 10 -1 8 0
  • 输出样例2
39 4 2
样例 2 解释

第 1. 2、4、5 棵树发生了苹果掉落的情况,因此 D=4。其中,连续三棵树都发生苹果掉落情况的有(5,1,2)和(4,5,1),因此 E=2。

【子任务】

在这里插入图片描述

  • mi≤1000,对所有 1≤i≤N

  • |aij|≤10^6, 对所有 1≤i≤N,1≤j≤mi

题解思路

思路几乎同第一题的小明种苹果,唯一需要重新记录的是一个数组flag[1001]存储所有苹果树的是否发生苹果掉落的信息。最后遍历这个标记数组,统计E值

题解中positive记录苹果树最新的正整数值,flag_minus记录最新的蔬果数。

注:每棵树若记录了该树已经是发生掉落的树了,需要判断一下,否则会重复记录 D 值。

该方法时间消耗低,空间消耗低。

题解(c/c++)

#include<bits/stdc++.h>
using namespace std;
int main() {
    int N, M, ai;
    int positive;
    int flag_minus;
    bool flag[1001] = {false};
    int T = 0, D = 0, E = 0;
    cin >> N;
    for (int i = 0; i < N; i++) {
        cin >> M >> positive;
        flag_minus = 0;
        for (int j = 1; j < M; j++) {
            cin >> ai;
            if (ai > 0) {
                if (!flag[i] && positive - flag_minus != ai) {
                    flag[i] = true;
                    D++;
                }
                positive = ai;
                flag_minus = 0;
            } else {
                flag_minus -= ai;
            }
        }
        T += positive - flag_minus;
    }
    for (int i = 0; i < N; i++) {
        if (flag[i] && flag[(i + 1) % N] && flag[(i + 2) % N]) {
            E++;
        }
    }
    cout << T << " " << D << " " << E << endl;
}
  • 6
    点赞
  • 6
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值