Задача о рюкзаке — различия между версиями
Margarita (обсуждение | вклад) |
Margarita (обсуждение | вклад) м |
||
| Строка 1: | Строка 1: | ||
| − | '''Задача о рюкзаке''' — дано <tex>k</tex> предметов, <tex> | + | '''Задача о рюкзаке''' — дано <tex>k</tex> предметов, <tex>k_i</tex> предмет имеет массу <tex> w_i > 0</tex> и стоимость <tex> p_i > 0</tex>. Необходимо выбрать из этих предметов такой набор, чтобы суммарная масса не превосходила заданной величины <tex>W</tex> (вместимость рюкзака), а суммарная стоимость была максимальна. |
== Формулировка задачи == | == Формулировка задачи == | ||
| Строка 15: | Строка 15: | ||
* Перебирая все подмножества набора из k предметов. Сложность такого решения <tex>O({2^{k}})</tex>. | * Перебирая все подмножества набора из k предметов. Сложность такого решения <tex>O({2^{k}})</tex>. | ||
| − | * Методом [[Meet-in-the-middle|Meet-in-the-middle] | + | * Методом [[Meet-in-the-middle|Meet-in-the-middle]]. Сложность решения <tex> O({2^{N/2}}\times{N}) </tex> |
| − | * Метод динамического | + | * Метод динамического программирования. Сложность - <tex>O(k \times W)</tex>. |
| − | == | + | == Метод динамического программирования == |
Пусть <tex>A(s, n)</tex> есть максимальная стоимости предметов, которые можно уложить в рюкзак вместимости n, если можно использовать только первые s предметов из заданных k. | Пусть <tex>A(s, n)</tex> есть максимальная стоимости предметов, которые можно уложить в рюкзак вместимости n, если можно использовать только первые s предметов из заданных k. | ||
| Строка 41: | Строка 41: | ||
== Реализация == | == Реализация == | ||
| − | Сначала генерируем <tex> | + | Сначала генерируем <tex>A</tex>. |
for i = 0..W | for i = 0..W | ||
| Строка 82: | Строка 82: | ||
{| class="wikitable" cellpadding="4" border="1" style="border-collapse: collapse;" | {| class="wikitable" cellpadding="4" border="1" style="border-collapse: collapse;" | ||
| + | |- | ||
| + | | || 0|| 1|| 2|| 3|| 4|| 5|| 6|| 7|| 8|| 9|| 10|| 11|| 12|| 13 | ||
|- | |- | ||
| s = 0|| 0|| 0|| 0|| 0|| 0|| 0|| 0|| 0|| 0|| 0|| 0|| 0|| 0|| 0 | | s = 0|| 0|| 0|| 0|| 0|| 0|| 0|| 0|| 0|| 0|| 0|| 0|| 0|| 0|| 0 | ||
| Строка 95: | Строка 97: | ||
| s = 5|| 0|| 0|| 0|| 1|| 6|| 6|| 6|| 7|| 7|| 10|| 10|| 10|| 13|| 13 | | s = 5|| 0|| 0|| 0|| 1|| 6|| 6|| 6|| 7|| 7|| 10|| 10|| 10|| 13|| 13 | ||
|} | |} | ||
| − | Числа от 0 до | + | Числа от 0 до 13 в первой строчке обозначают вместимость рюкзака. |
| + | |||
| + | В первой строке как только вместимость рюкзака <tex>n \ge 3</tex>, добавляем в рюкзак 1 предмет. | ||
| + | |||
| + | Рассмотрим <tex>s = 3</tex>, при каждом <tex>n \ge 5 (</tex>так как <tex>w_3 = 5)</tex> сравниваем <tex>A[s-1][n] и A[s-1][n-w_3]+p_3</tex> и записываем в <tex>A[s][n]</tex> стоимость либо рюкзака без третьего предмета, но с таким же весом, либо с третьим предметом, тогда стоимость равна стоимость третьего предмета плюс стоимость рюкзака с вместимостью на <tex>w_3</tex> меньше. | ||
| + | |||
| + | Максимальная стоимость рюкзака находится в <tex>A(5, 13)</tex>. | ||
| + | |||
| + | '''Теперь восстановим набор предметов, из которых состоит максимально дорогой рюкзак.''' | ||
| + | |||
| + | |||
| + | |||
| + | |||
| + | |||
| + | |||
| + | |||
| + | |||
| + | |||
| + | |||
| + | |||
| + | |||
| + | |||
| + | |||
| − | |||
| − | |||
| − | |||
| − | |||
| − | |||
| − | |||
| − | |||
| − | |||
| − | |||
Таким образом, набор состоит из <tex>1, 2, 5</tex> предметов. | Таким образом, набор состоит из <tex>1, 2, 5</tex> предметов. | ||
Версия 14:12, 27 декабря 2012
Задача о рюкзаке — дано предметов, предмет имеет массу и стоимость . Необходимо выбрать из этих предметов такой набор, чтобы суммарная масса не превосходила заданной величины (вместимость рюкзака), а суммарная стоимость была максимальна.
Содержание
Формулировка задачи
Дано предметов, - вместимость рюкзака, — соответствующий ему набор положительных целых весов, — соответствующий ему набор положительных целых стоимостей. Нужно определить набор бинарных величин , где , если предмет включен в набор, , если предмет не включен, такой что:
- максимальна.
Варианты решения
Задачу о рюкзаке можно решить несколькими способами:
- Перебирая все подмножества набора из k предметов. Сложность такого решения .
- Методом Meet-in-the-middle. Сложность решения
- Метод динамического программирования. Сложность - .
Метод динамического программирования
Пусть есть максимальная стоимости предметов, которые можно уложить в рюкзак вместимости n, если можно использовать только первые s предметов из заданных k.
Найдем . Возможны 2 варианта:
- Если предмет не попал в рюкзак. Тогда
- Если попал в рюкзак. Тогда
Таким образом:
Теперь найдем набор предметов, входящих в рюкзак.
Рассмотрим входит ли - последний предмет в рюкзак. Если равно , значит последний предмет не входит в набор, иначе входит. Так рекусривно идем до первого предмета. Получаем искомый набор.
Реализация
Сначала генерируем .
for i = 0..W
A[0][i] = 0
for i = 0..k
A[i][0] = 0 //Первые элементы приравниваем 0
for s = 1..k
for n = 0..W //Перебираем для каждого s, все n
if n >= w[s] //Если текущий предмет можно положить в рюкзак
A[s][n] = max(A[s-1][n], A[s-1][n-w[s]]+p[s]) //выбираем класть его или нет
else
A[s][n] = A[s-1][n] //иначе, не кладем
Затем найдем набор предметов, входящих в рюкзак, рекурсивной функцией:
findAns(s, n)
if A[s][n] == 0
return
if A[s-1][n] == A[s][n]
findAns(s-1, n)
else
findAns(s-1, n - w[s]);
ans.push(s);
Сложность алгоритма
Пример
| 0 | 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | 10 | 11 | 12 | 13 | |
| s = 0 | 0 | 0 | 0 | 0 | 0 | 0 | 0 | 0 | 0 | 0 | 0 | 0 | 0 | 0 |
| s = 1 | 0 | 0 | 0 | 1 | 1 | 1 | 1 | 1 | 1 | 1 | 1 | 1 | 1 | 1 |
| s = 2 | 0 | 0 | 0 | 1 | 6 | 6 | 6 | 7 | 7 | 7 | 7 | 7 | 7 | 7 |
| s = 3 | 0 | 0 | 0 | 1 | 6 | 6 | 6 | 7 | 7 | 10 | 10 | 10 | 11 | 11 |
| s = 4 | 0 | 0 | 0 | 1 | 6 | 6 | 6 | 7 | 7 | 10 | 10 | 10 | 13 | 13 |
| s = 5 | 0 | 0 | 0 | 1 | 6 | 6 | 6 | 7 | 7 | 10 | 10 | 10 | 13 | 13 |
Числа от 0 до 13 в первой строчке обозначают вместимость рюкзака.
В первой строке как только вместимость рюкзака , добавляем в рюкзак 1 предмет.
Рассмотрим , при каждом так как сравниваем и записываем в стоимость либо рюкзака без третьего предмета, но с таким же весом, либо с третьим предметом, тогда стоимость равна стоимость третьего предмета плюс стоимость рюкзака с вместимостью на меньше.
Максимальная стоимость рюкзака находится в .
Теперь восстановим набор предметов, из которых состоит максимально дорогой рюкзак.
Таким образом, набор состоит из предметов.
Стоимость рюкзака
Вес рюкзака