📅  最后修改于: 2023-12-03 15:23:04.120000             🧑  作者: Mango
这是一道关于数据结构的编程题。题目描述如下:
一个长度为n的正整数序列,每个元素都是1到n之间的数。定义一个数为“左儿子”,当它在序列中是它左边第一个比它小的数;定义一个数为“右儿子”,当它在序列中是它右边第一个比它小的数。如果左儿子和右儿子都不存在,则称该数为“根”。
现在给定一个长度为n的正整数序列,请你编写程序,计算所有非根节点的左儿子和右儿子的和。
函数签名如下:
def left_right_sum(n, a):
pass
第一行输入一个正整数 $n$,表示序列长度。
第二行输入 $n$ 个正整数,表示序列中的元素。
输出所有非根节点的左儿子和右儿子的和。
5
5 6 1 7 5
12
算法思路:
遍历整个序列即可,利用栈维护一个递减的序列,如果下一个数字比栈顶元素大,就说明栈顶元素的右子节点就是这个数,此时将栈顶元素出栈,直到遇到第一个比下一个数大的数为止;否则就将这个数入栈。栈中每个数在遍历完整个数列之前,如果它左边没有更小的数,那么它就是一个根节点;否则就可以计算出它的左儿子,也可以计算出它的右儿子。
def left_right_sum(n, a):
stack = []
res = 0
for i in range(n):
while len(stack) > 0 and a[stack[-1]] > a[i]:
res += i + 1
res += stack[-1]
stack.pop()
stack.append(i)
while len(stack) > 0:
res += stack[-1] + 1
stack.pop()
return res
调用函数:
n = 5
a = [5, 6, 1, 7, 5]
print(left_right_sum(n, a)) # 12
注意事项: