|
| 1 | +# Time: O(n * p * g) |
| 2 | +# Space: O(p * g) |
| 3 | + |
| 4 | +# There are G people in a gang, and a list of various crimes they could commit. |
| 5 | +# |
| 6 | +# The i-th crime generates a profit[i] and requires group[i] gang members to participate. |
| 7 | +# |
| 8 | +# If a gang member participates in one crime, |
| 9 | +# that member can't participate in another crime. |
| 10 | +# |
| 11 | +# Let's call a profitable scheme any subset of these crimes that |
| 12 | +# generates at least P profit, |
| 13 | +# and the total number of gang members participating in that subset of crimes is at most G. |
| 14 | +# |
| 15 | +# How many schemes can be chosen? Since the answer may be very large, return it modulo 10^9 + 7. |
| 16 | +# |
| 17 | +# Example 1: |
| 18 | +# |
| 19 | +# Input: G = 5, P = 3, group = [2,2], profit = [2,3] |
| 20 | +# Output: 2 |
| 21 | +# Explanation: |
| 22 | +# To make a profit of at least 3, the gang could either commit crimes 0 and 1, or just crime 1. |
| 23 | +# In total, there are 2 schemes. |
| 24 | +# Example 2: |
| 25 | +# |
| 26 | +# Input: G = 10, P = 5, group = [2,3,5], profit = [6,7,8] |
| 27 | +# Output: 7 |
| 28 | +# Explanation: |
| 29 | +# To make a profit of at least 5, the gang could commit any crimes, as long as they commit one. |
| 30 | +# There are 7 possible schemes: (0), (1), (2), (0,1), (0,2), (1,2), and (0,1,2). |
| 31 | +# |
| 32 | +# Note: |
| 33 | +# - 1 <= G <= 100 |
| 34 | +# - 0 <= P <= 100 |
| 35 | +# - 1 <= group[i] <= 100 |
| 36 | +# - 0 <= profit[i] <= 100 |
| 37 | +# - 1 <= group.length = profit.length <= 100 |
| 38 | + |
| 39 | +import itertools |
| 40 | + |
| 41 | + |
| 42 | +class Solution(object): |
| 43 | + def profitableSchemes(self, G, P, group, profit): |
| 44 | + """ |
| 45 | + :type G: int |
| 46 | + :type P: int |
| 47 | + :type group: List[int] |
| 48 | + :type profit: List[int] |
| 49 | + :rtype: int |
| 50 | + """ |
| 51 | + dp = [[0 for _ in xrange(G+1)] for i in xrange(P+1)] |
| 52 | + dp[0][0] = 1 |
| 53 | + for p, g in itertools.izip(profit, group): |
| 54 | + for i in reversed(xrange(P+1)): |
| 55 | + for j in reversed(xrange(G-g+1)): |
| 56 | + dp[min(i+p, P)][j+g] += dp[i][j] |
| 57 | + return sum(dp[P]) % (10**9 + 7) |
0 commit comments