可见的山峰对数量
題目:一個不含有負數的數組可以代表一圈環形山,每個位置的值代表山的高度,比如{3,1,2,4,5}、{4,5,3,1,2}或{1,2,4,5,3}都代表同樣結構的環形山。3->1->2->4->5->3方向叫做next方向(逆時針),3->5->4->2->1->3方向叫做last方向叫做last方向(順時針)
山峰A和山峰B能夠相互看見的條件為:
1、如果A和B是同一座山,認為互相看不見
2、如果A和B是不同的山,并且在環中相鄰,認為可以相互看見
3、如果A和B是不同的山,并且在環中不相鄰,假設兩座山高度最小值為min。如果A通過next方向到B的途中沒有高度比min大的山峰,或者A通過last方向到B的途中沒有高度比min大的山峰,認為A和B可以相互看見
給定一個不含負數且沒有重復值的數組arr,請返回有多少對山峰可以互相看見
進階問題:給定一個不含油負數但可能含有重復值的數組arr,返回有多少對山峰能夠相互看見
要求:如果arr的長度為N,沒有重復值的情況下時間復雜度達到O(1),可能有重復值的情況下時間復雜度為O(N)
思路:數組中所有數字不一樣,環形結構只有1座山峰,可見山峰對為0;環形結構中只有兩座山峰時,可見山峰的數量為1.環形結構中有i座山峰時(i>2)可見山峰對的數量為2i-3.? 高度小的山峰去找高度大的山峰。
進階代碼:
def getVisibNum(L):if L == None or len(L) < 2:return 0#找到最大值所在位置maxIndex = 0for in in range(len(L)):if L[maxIndex] < L[i]:maxIndex = istack = []stack.append([L[maxIndex],1])index = nextIndex(maxIndex,len(L))res = 0while index!=maxIndex:while stack[-1][0] < L[index]:k = stack.pop()[1]res += getNum(k) + 2*kif stack[-1][0] == L[index]:stack[-1][1] += 1else:stack.append([L[index],1])index = nextIndex(maxIndex,len(L))while len(stack) > 2:times = stack.pop()[1]res += getNum(times) + 2* timeswhile len(stack) == 2:times = stack.pop()[1]if stack[-1][1] == 1:res += getNum(times) + timeselse:res += getNum(times) + 2 * timesres + = getNum(stack.pop()[1])def nextIndex(k,size):if k < (size-1):return k + 1else:return 0def getNum(k):if k == 1:return 0 else:return (k*(k-1))/2?
總結
- 上一篇: 求最大子矩阵的大小
- 下一篇: 遍历二叉树的神级方法(Morris遍历)