P9810 [CCC 2015 S1] Zero That Out

题目传送门

思路:

题目要求我们维护一个序列,并根据给定的操作进行添加和删除元素,最后计算序列中所有数的和。我们可以使用栈来实现这个功能,因为栈的特性非常适合处理这种在序列末尾添加和删除元素的操作。

栈:

栈(Stack)是一种线性数据结构,遵循后进先出(Last In, First Out,LIFO)的原则。栈的基本操作包括:

  1. push:将元素压入栈顶。
  2. pop:从栈顶移除元素。
  3. top(或 peek):查看栈顶元素,但不移除它。
  4. empty:检查栈是否为空。

栈在计算机科学中有广泛的应用,例如函数调用栈、表达式求值、括号匹配检查等。

具体步骤:

  1. 初始化栈:创建一个栈来存储序列中的元素。
  2. 读取操作次数:读取整数 k,表示操作的次数。
  3. 执行操作
    • 循环读取 k 次操作:
      • 如果读取到的数 a 为 0,则表示删除最后一个加入的数,调用 stack.pop()
      • 如果 a 不为 0,则将 a 加入序列,调用 stack.push(a)
  4. 计算最终序列的和
    • 使用一个变量 sum 来累加栈中的元素。
    • 遍历栈中的元素,累加到 sum 变量中,同时每次循环都调用 stack.pop() 来移除栈顶元素。
  5. 输出结果:输出最终序列的和 sum

代码&解释:

c++代码:

#include <iostream>
#include <stack>
using namespace std;

int main() {
    int k;
    cin >> k;
    
    stack<int> sequence;
    
    for (int i = 0; i < k; ++i) {
        int a;
        cin >> a;
        
        if (a == 0) {
            sequence.pop();
        } else {
            sequence.push(a);
        }
    }
    
    int sum = 0;
    while (!sequence.empty()) {
        sum += sequence.top();
        sequence.pop();
    }
    
    cout << sum << endl;
    
    return 0;
}

 代码解释:

  1. 包含头文件

    • #include <iostream>:用于输入输出操作。
    • #include <stack>:用于使用STL中的栈。
  2. 使用命名空间

    • using namespace std;:使得我们可以直接使用标准库中的名称,而不需要每次都加上 std:: 前缀。
  3. 主函数

    • int main() {:程序从这里开始执行。
  4. 读取操作次数

    • int k;:声明一个整数变量 k
    • cin >> k;:读取一个整数 k,表示接下来要进行的操作次数。
  5. 初始化栈

    • stack<int> sequence;:创建一个 stack<int> 类型的栈 sequence,用于存储序列中的元素。
  6. 执行操作

    • for (int i = 0; i < k; ++i) {:使用 for 循环读取 k 次操作。
    • int a;:声明一个整数变量 a
    • cin >> a;:读取一个整数 a
    • if (a == 0) {:如果 a 为 0,调用 sequence.pop() 删除栈顶元素。
    • } else {:如果 a 不为 0,调用 sequence.push(a) 将 a 压入栈顶。
    • }:结束 if-else 语句。
    • }:结束 for 循环。
  7. 计算最终序列的和

    • int sum = 0;:声明一个整数变量 sum 并初始化为 0
    • while (!sequence.empty()) {:使用 while 循环遍历栈中的元素,直到栈为空。
    • sum += sequence.top();:将栈顶元素加到 sum 中。
    • sequence.pop();:移除栈顶元素。
    • }:结束 while 循环。
  8. 输出结果

    • cout << sum << endl;:输出最终序列的和 sum
  9. 返回值

    • return 0;:程序正常结束,返回 0

如果诸位大佬没有学过栈,你可以用动态数组模拟栈: 
#include <iostream>
using namespace std;

int main(){
    int k;
    cin>>k;
    
    int* sequence = new int[k]; 
    int top = -1; 
    
    for (int i = 0;i < k;++i){
        int a;
        cin>>a;
        
        if(a == 0) {--top;}
        else{sequence[++top] = a;}
    }
    
    int sum = 0;
    for (int i = 0;i <= top;++i){sum += sequence[i];}
    
    cout<<sum<<endl;
    return 0;
}

代码解释:

  1. 输入部分

    • 首先读取整数 k,表示操作的次数。
    • 创建一个动态数组 sequence 来模拟栈,大小为 k
    • 使用 top 变量来跟踪栈顶的位置,初始值为 -1 表示栈为空。
  2. 操作部分

    • 循环读取 k 次操作:
      • 如果读取到的数 a 为 0,则表示删除最后一个加入的数,即将 top 减 1
      • 如果 a 不为 0,则将 a 加入序列,即将 a 赋值给 sequence[++top]
  3. 计算最终序列的和

    • 遍历从 0 到 top 的元素,累加到 sum 变量中。
  4. 输出结果

    • 输出最终序列的和 sum
  5. 释放动态数组

    • 使用 delete[] 释放动态分配的数组 sequence

Python代码:

def main():
    k = int(input())
    sequence = []
    
    for _ in range(k):
        a = int(input())
        if a == 0:
            sequence.pop()
        else:
            sequence.append(a)
    
    sum_result = sum(sequence)
    print(sum_result)

if __name__ == "__main__":
    main()

代码解释:

  1. 读取操作次数

    • k = int(input()):读取一个整数 k,表示接下来要进行的操作次数。
  2. 初始化列表

    • sequence = []:创建一个空列表 sequence,用于存储序列中的元素。
  3. 执行操作

    • for _ in range(k)::使用 for 循环读取 k 次操作。
    • a = int(input()):读取一个整数 a
    • if a == 0::如果 a 为 0,调用 sequence.pop() 删除列表最后一个元素。
    • else::如果 a 不为 0,调用 sequence.append(a) 将 a 添加到列表末尾。
  4. 计算最终序列的和

    • sum_result = sum(sequence):计算列表中所有元素的和。
  5. 输出结果

    • print(sum_result):输出最终序列的和 sum_result

Pascal代码(现打的,没试过,仅供参考):

program ZeroThatOut;
uses sysutils;

var
    k, a, i, sum, top: integer;
    sequence: array of integer;

begin
    readln(k);
    setlength(sequence, k);
    top := -1;
    
    for i := 0 to k - 1 do
    begin
        readln(a);
        if a = 0 then
        begin
            if top >= 0 then
            begin
                dec(top);
            end;
        end
        else
        begin
            inc(top);
            sequence[top] := a;
        end;
    end;
    
    sum := 0;
    for i := 0 to top do
    begin
        sum := sum + sequence[i];
    end;
    
    writeln(sum);
end.

代码解释:

  1. 读取操作次数

    • readln(k);:读取一个整数 k,表示接下来要进行的操作次数。
  2. 初始化动态数组

    • setlength(sequence, k);:创建一个动态数组 sequence,初始大小为 k
    • top := -1;:初始化 top 为 -1,表示栈为空。
  3. 执行操作

    • for i := 0 to k - 1 do:使用 for 循环读取 k 次操作。
    • readln(a);:读取一个整数 a
    • if a = 0 then:如果 a 为 0,并且栈不为空(top >= 0),则调用 dec(top) 删除栈顶元素。
    • else:如果 a 不为 0,调用 inc(top) 增加栈顶指针,并将 a 添加到栈顶位置 sequence[top]
  4. 计算最终序列的和

    • sum := 0;:初始化 sum 为 0
    • for i := 0 to top do:遍历栈中的所有元素。
    • sum := sum + sequence[i];:将栈中的元素加到 sum 中。
  5. 输出结果

    • writeln(sum);:输出最终序列的和 sum

希望这些代码能帮助您理解并解决这个问题,如果有问题,请随时提问。
  蒟蒻题解,神犇勿喷,点个赞再走吧!QAQ
  • 20
    点赞
  • 21
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值