题目:有个马戏团正在设计叠罗汉的表演节目,一个人要站在另一人的肩膀上。出于实际和美观的考虑,在上面的人要比下面的人矮一点且轻一点。已知马戏团每个人的身高和体重,请编写代码计算叠罗汉最多能叠几个人。
思想:需要同时维护两个维度(身高、体重)同时递增。将两个维度合并成一组数据,并将一个维度按升序排序(当该维度中多个值相等时,将另一维度按降序排序)。接下来的任务便是再另一个维度中找出最长升序子序列。其方法是维护一个递增dp数组。对于当前扫描元素i来讲,当i的体重大于dp最后一个元素时,dp数组直接添加i的体重。否则,从dp数组中找出第一个大于i的体重的值,将其替换为i的体重值。由于dp数组是按升序排列的,因此可以使用二分查找法。
class Solution:
def bestSeqAtIndex(self, height: List[int], weight: List[int]) -> int:
if len(height) < 2:
return len(height)
vals = list(zip(height,weight))
vals.sort(key = lambda x: (x[0],-x[1]))
dp = [vals[0][1]]
for i in range(1,len(vals)):
if vals[i][1] > dp[-1]:
dp.append(vals[i][1])
else:
left = 0
right = len(dp)-1
while left <= right:
if vals[i][1] <= dp[left]:
dp[left] = vals[i][1]
break
else:
mid = (left+right)//2
if dp[mid] < vals[i][1]:
left = mid + 1
else:
right = mid
return len(dp)