1.题目
有个马戏团正在设计叠罗汉的表演节目,一个人要站在另一人的肩膀上。出于实际和美观的考虑,在上面的人要比下面的人矮一点且轻一点。已知马戏团每个人的身高和体重,请编写代码计算叠罗汉最多能叠几个人。
示例:
输入:height = [65,70,56,75,60,68]
weight = [100,150,90,190,95,110]
输出:6
解释:从上往下数,叠罗汉最多能叠 6 层:
(56,90), (60,95), (65,100), (68,110), (70,150), (75,190)
提示:
height.length == weight.length <= 10000
2.解答
如何把height进行升序排序,那么就是对weight进行统计最长上升子序列。实现O(n^2)的算法比较容易,但会超时,这里采用了二分法实现,复杂度O(nlogn).
小注意点是,height身高相同,weight进行降序排序。(也就是height升序,weight降序),满足题目的严格递增要求。
此外,也可以,分别对height,weight进行排序,获得index数组,找出两个数组最大公共子数组。
class Solution:
def lengthOfLIS(self, nums: [int]) -> int:
tails, res = [0] * len(nums), 0
for num in nums:
i, j = 0, res
while i < j:
m = (i + j) // 2
if tails[m] < num: i = m + 1 # 如果要求非严格递增,将此行 '<' 改为 '<=' 即可。
else: j = m
tails[i] = num
if j == res: res += 1
return res
def bestSeqAtIndex(self, height: List[int], weight: List[int]) -> int:
if len(height)==0:
return 0
height,weight = zip(*sorted(list(zip(height,weight)),key=lambda x:(x[0],-x[1])))
result = self.lengthOfLIS(weight)
return result