输入的第一行是一个整数N(2 <= N <= 100),表示同学的总数。 第一行有n个整数,用空格分隔,第i个整数Ti(130 <= Ti <= 230)是第i位同学的身高(厘米)。
可能包括多组测试数据,对于每组数据, 输出包括一行,这一行只包含一个整数,就是最少需要几位同学出列。
8 186 186 150 200 160 130 197 220
4
import sys line = sys.stdin.readline().strip() n = int(line) line = sys.stdin.readline().strip() h = list(map(int, line.split())) def lengthOfLIS(nums): m = len(nums) if(m == 0): return 0 dp = [0 for i in range(m)] maxx = 1 for i in range(m): maxn = 1 for j in range(i): if (nums[i] > nums[j]): maxn = max(maxn, dp[j] + 1) dp[i] = maxn maxx = max(maxn,maxx) return maxx minn = n for i in range(1,n): t = lengthOfLIS(h[:i]) q = h[i-1:] q = q[::-1] s = lengthOfLIS(q) minn = min(n - t - s + 1, minn) print(minn)
两个动态规划,找出左到右递增时最长子序列长度,右到左递增时最长子序列长度。
然后相同下标相加长度相加-1就得到题目要求的队形长度。就可以得到去除的人数
#找出一个方向上的递增子序列长度
def findAscSubString(peopleNum, heightList):
ascSubNum = [1] * peopleNum
for i in range(peopleNum):
if heightList[i] != min(heightList[:i + 1]):
for j in range(i):
if heightList[i] > heightList[j]:
if ascSubNum[i] < ascSubNum[j] + 1:
ascSubNum[i] = ascSubNum[j] + 1
return ascSubNum
#得到去除的队员人数
def findRemovePeople(peopleNum, heightList):
leftPeople = findAscSubString(peopleNum, heightList) #左到右递增
rightPeople = findAscSubString(peopleNum, heightList[::-1]) #右到左递增
rightPeople.reverse() #反转得到下标对应
stayPeople = 0
for i in range(peopleNum):
if stayPeople < leftPeople[i] + rightPeople[i]:
stayPeople = leftPeople[i] + rightPeople[i]
return peopleNum - stayPeople + 1
while True:
try:
peopleNum = int(input())
heightList = list(map(int, input().split()))
print(findRemovePeople(peopleNum, heightList))
except Exception:
break