空栈压数
题目描述
向一个空栈压入正整数, 每当压入一个整数时, 执行以下规则 (设: 栈顶至栈底整数依次编号为 n1, n2, ..., nx, 其中n1 为最新压入的整数)
- 如果 n1 = n2, 则 n1/n2全部出栈, 压入新数据 m, m = 2 * n1
- 如果 n1 = n2 + ... + ny (y的范围为[3, x]), 则 n1, n2, ..., ny 全部出栈, 压入新数据 m, m = 2 * n1.
- 如果上述规则都不满足, 则不做操作.
例如: 依次向栈压入 6/1/2/3:
- 当压入 2 时, 栈顶至栈底依次为 [2,1,6].
- 当压入 3 时, 3 = 2 + 1, 3/2/1 全部出栈, 重新入栈整数6, 此时栈顶至栈底依次为 [6, 6]; 6 = 6, 两个 6 全部出栈, 压入 12.
- 最终栈中只剩个元素 12.
输入
使用单个空格隔开的正整数的字符串, 如 5 6 7 8
, 左边的数字先入栈.
- 正整数大小为 [1, 2^31−1]
- 正整数个数为 [1,1000]
输出
最终栈中存留的元素值, 元素值使用单个空格隔开, 如 8 7 6 5
, 从左至右依次为栈顶至栈底的数字.
示例1
输入:
10 20 50 80 1 1
输出:
2 160
示例2
输入:
5 10 20 50 85 1
输出:
1 170
题解
Python
def main():
# 读取输入, 并将它们转换成正整数
# 然后创建一个空的栈
# 遍历所有的正整数, 依次入栈
# 每次入栈时做以下检查:
# 1. 如果 n1=n2, 则它们全出栈, 然后自动入栈 2 * n1
# 2. 如果 n1=sum(n2, n3..), 则它们全出栈, 然后自动入栈 2 * n1
# 最后打印栈中剩下的整数
numbers = list(map(int, input().split()))
stack = []
for number in numbers:
# 检查规则1
if stack and stack[-1] == number:
stack[-1] += number
continue
top_sum = 0
will_append = True
# 从栈顶开始求和
for i in range(len(stack) - 1, -1, -1):
top_sum += stack[i]
if top_sum > number:
# 不满足
break
elif top_sum == number:
# 满足规则2
for j in range(len(stack) - 1, i - 1, -1):
stack.pop()
stack.append(number * 2)
will_append = False
break
if will_append:
# 如果上面的规则不满足, 就把该整数入栈
stack.append(number)
# 打印结果
s = " ".join(map(str, reversed(stack)))
print(s)
if __name__ == "__main__":
main()
Rust
use std::cmp::Ordering; use std::io::{stdin, BufRead}; fn solution() { // 读取输入, 并将它们转换成正整数 // 然后创建一个空的栈 // 遍历所有的正整数, 依次入栈 // 每次入栈时做以下检查: // 1. 如果 n1=n2, 则它们全出栈, 然后自动入栈 2 * n1 // 2. 如果 n1=sum(n2, n3..), 则它们全出栈, 然后自动入栈 2 * n1 // 最后打印栈中剩下的整数 let mut line = String::new(); let ret = stdin().lock().read_line(&mut line); assert!(ret.is_ok()); let numbers: Vec<i32> = line .split_ascii_whitespace() .map(|s| s.parse().unwrap()) .collect(); let mut stack: Vec<i32> = Vec::new(); for &number in &numbers { // 检查规则1 if stack.last() == Some(&number) { stack.pop(); stack.push(number * 2); continue; } let mut top_sum = 0; let mut will_append = true; // 从栈顶开始求和 for i in (0..stack.len()).rev() { top_sum += stack[i]; match top_sum.cmp(&number) { Ordering::Greater => { // 不满足 break; } Ordering::Equal => { // 满足规则2 stack.resize(i, 0); stack.push(number * 2); will_append = false; break; } _ => (), } } if will_append { // 如果上面的规则不满足, 就把该整数入栈 stack.push(number); } } // 打印结果 let out = stack .into_iter() .rev() .map(|x| x.to_string()) .collect::<Vec<_>>() .join(" "); println!("{out}"); } fn main() { solution(); }