Похоже, что модификация рюкзака решит эту проблему.
давайте определим нашу таблицу dp как 4-мерный массив dp [N + 1] [A + 1] [B + 1] [C + 1]
теперь некоторая ячейка dp [n] [a] [b] [c] означает, что мы рассмотрели n магазинов, из них мы выбрали магазины для мяса, b магазины для тортов и c магазины для пиццы, и в нем хранится максимум энергии, который мы можем иметь.
Переходы также просты, из некоторого состояния dp [n] [a] [b] [c] мы можем перейти к:
Осталось только заполнить дп таблицу. Пример кода:
N = 10
A,B,C = 5,3,2
energy = [
[56, 44, 41],
[56, 84, 45],
[40, 98, 49],
[91, 59, 73],
[69, 94, 42],
[81, 64, 80],
[55, 76, 26],
[63, 24, 22],
[81, 60, 44],
[52, 95, 11]
]
dp = {}
for n in range(N+1):
for a in range(A+1):
for b in range(B+1):
for c in range(C+1):
dp[n,a,b,c]=0
answer = 0;
for n in range(N+1):
for a in range(A+1):
for b in range(B+1):
for c in range(C+1):
#Case 1, skip n-th shop
if (n+1,a,b,c) in dp: dp[n+1,a,b,c] = max(dp[n+1,a,b,c], dp[n,a,b,c])
#Case 2, buy meat from n-th shop
if (n+1,a+1,b,c) in dp: dp[n+1,a+1,b,c] = max(dp[n+1,a+1,b,c], dp[n,a,b,c] + energy[n][0])
#Case 3, buy cake from n-th shop
if (n+1,a,b+1,c) in dp: dp[n+1,a,b+1,c] = max(dp[n+1,a,b+1,c], dp[n,a,b,c] + energy[n][1])
#Case 4, buy pizza from n-th shop
if (n+1,a,b,c+1) in dp: dp[n+1,a,b,c+1] = max(dp[n+1,a,b,c+1], dp[n,a,b,c] + energy[n][2])
answer = max(answer,dp[n,a,b,c])
print(answer)
Если Вы пишете EventGetSum()
это сразу называет метод EventGetSum.
Если Вы пишете new EventHandler(EventGetSum)
это создает делегата, который (в свою очередь) назовет EventGetSum, когда он будет вызван.
Вызов к Control.Invoke
вызывает данного делегата от потока UI, ответственного за управление. Это необходимо, потому что Вы не должны получать доступ к элементам UI от произвольных потоков.
Это выполняется EventGetSum
метод в потоке к этому окно this
принадлежит.
Это обычно используется при контакте с перекрестным потоком вызовов UI.
Посмотрите на документацию MSDN для ISynchronizeInvoke.