当前位置:   article > 正文

蓝桥杯 第四十八天 线性DP && 背包回顾_dp = [1 for i in range(n)] for j in range(m)

dp = [1 for i in range(n)] for j in range(m)

目录

1.187. 导弹防御系统 - AcWing题库

2.最长公共子序列

3.最长上升子序列

4.272. 最长公共上升子序列 - AcWing题库

5.01背包

(1)最初解法

6.983. 最低票价 - 力扣(LeetCode) (leetcode-cn.com)


1.187. 导弹防御系统 - AcWing题库

  1. def dfs(num,l,d):
  2. global ans
  3. if l+d>=ans:
  4. return
  5. if num==n:
  6. ans=l+d
  7. return
  8. k=0
  9. while k<l and up[k]>=a[num]:
  10. k+=1
  11. temp=up[k]
  12. up[k]=a[num]
  13. if k<l:
  14. dfs(num+1,l,d)
  15. else:
  16. dfs(num+1,l+1,d)
  17. up[k]=temp
  18. k=0
  19. while k<d and down[k]<=a[num]:
  20. k+=1
  21. temp=down[k]
  22. down[k]=a[num]
  23. if k<d:
  24. dfs(num+1,l,d)
  25. else:
  26. dfs(num+1,l,d+1)
  27. down[k]=temp
  28. while True:
  29. n=int(input())
  30. if n==0:
  31. break
  32. a=list(map(int,input().split()))
  33. up=[0 for i in range(n)]
  34. down=[0 for i in range(n)]
  35. ans=n
  36. dfs(0,0,0)
  37. print(ans)

2.最长公共子序列

  1. n=int(input())
  2. a=list(map(int,input().split()))
  3. b=list(map(int,input().split()))
  4. dp=[[0 for i in range(n+1)]for j in range(n+1)]
  5. for i in range(1,n+1):
  6. for j in range(1,n+1):
  7. dp[i][j]=max(dp[i-1][j],dp[i][j-1])
  8. if a[i-1]==b[j-1]:
  9. dp[i][j]=dp[i-1][j-1]+1
  10. print(dp[-1][-1])

3.最长上升子序列

  1. n=int(input())
  2. a=[-1<<31]+list(map(int,input().split()))
  3. dp=[0 for i in range(n+1)]
  4. for i in range(1,n+1):
  5. for j in range(i):
  6. if a[i]>=a[j]:
  7. dp[i]=max(dp[i],dp[j]+1)
  8. print(dp[-1])

4.272. 最长公共上升子序列 - AcWing题库

  1. n=int(input())
  2. a=[0]+list(map(int,input().split()))
  3. b=[0]+list(map(int,input().split()))
  4. dp=[[0 for i in range(n+1)]for j in range(n+1)]
  5. for i in range(1,n+1):
  6. maxv=1
  7. for j in range(1,n+1):
  8. dp[i][j]=dp[i-1][j]
  9. if a[i]==b[j]:
  10. dp[i][j]=max(dp[i][j],maxv)
  11. if b[j]<a[i]:
  12. maxv=max(maxv,dp[i][j]+1)
  13. # for k in range(1,j):
  14. # if b[k]<a[i]:
  15. # dp[i][j]=max(dp[i][j],dp[i-1][k]+1)
  16. # else:
  17. # dp[i][j]=dp[i-1][j]
  18. for i in dp:
  19. print(i)
  20. print(max(dp[-1]))

5.01背包

昨晚的模拟赛,今晚的最长公共上升子序列让我发现我的dp有很大的问题,回去复习01背包,果然发现问题很大

(1)最初解法

dp永远都是状态的继承,01背包问题,在当前的决策上,有两种

第一种,我不要第i个物品,代码如下,这是无论如何都要继承的

无论如何的意思是,不管当年这个物品的体积能否放得下, 这个物品的价值如何,我们都有可能从这个状态转移来,所以记住这个无论如何

dp[i][j]=dp[i-1][j]

第二种,要第i个物品,这时候就不能无论如何了,因为你得考虑当前背包的容量能否容纳这个物品。如果这个背包可以容纳,那么就可以尝试更新一下,这里的max函数其实比较的第二种和第一种状态继承时的大小

  1. if j>=vs[i]:
  2. dp[i][j]=max(dp[i][j],dp[i-1][j-vs[i]]+w[i])

最终代码

  1. n,v=map(int,input().split())
  2. dp=[[0 for i in range(v+1)]for j in range(n+1)]
  3. vs,w=[0],[0]
  4. for i in range(n):
  5. vi,wi=map(int,input().split())
  6. vs.append(vi)
  7. w.append(wi)
  8. for i in range(1,n+1):
  9. for j in range(1,v+1):
  10. dp[i][j]=dp[i-1][j]
  11. if j>=vs[i]:
  12. dp[i][j]=max(dp[i][j],dp[i-1][j-vs[i]]+w[i])
  13. print(dp[-1][-1])

6.983. 最低票价 - 力扣(LeetCode) (leetcode-cn.com)

  1. class Solution:
  2. def mincostTickets(self, days: List[int], costs: List[int]) -> int:
  3. dp=[0 for i in range(max(days)+1)]
  4. for i in range(1,max(days)+1):
  5. if i not in days:
  6. dp[i]=dp[i-1]
  7. else:
  8. x1=max(i-1,0)
  9. x2=max(i-7,0)
  10. x3=max(i-30,0)
  11. dp[i]=min(dp[x1]+costs[0],dp[x2]+costs[1],dp[x3]+costs[2])
  12. return dp[-1]

声明:本文内容由网友自发贡献,不代表【wpsshop博客】立场,版权归原作者所有,本站不承担相应法律责任。如您发现有侵权的内容,请联系我们。转载请注明出处:https://www.wpsshop.cn/w/菜鸟追梦旅行/article/detail/415916
推荐阅读
相关标签
  

闽ICP备14008679号