mirror of
https://github.com/krahets/hello-algo.git
synced 2026-07-08 03:56:47 +08:00
deploy
This commit is contained in:
@@ -4339,23 +4339,23 @@
|
||||
<ul>
|
||||
<li>Динамическое программирование раскладывает задачу на подзадачи и повышает вычислительную эффективность за счет хранения решений этих подзадач и устранения повторных вычислений.</li>
|
||||
<li>Если не учитывать затраты времени, то любую задачу динамического программирования можно решить с помощью поиска с возвратом (полного перебора), однако в дереве рекурсии возникает множество перекрывающихся подзадач, из-за чего эффективность крайне низка. После введения таблицы памяти можно хранить решения всех уже вычисленных подзадач и гарантировать, что каждая перекрывающаяся подзадача будет вычисляться только один раз.</li>
|
||||
<li>Поиск с мемоизацией - это рекурсивный метод "сверху вниз", а соответствующее ему динамическое программирование - это итеративный метод "снизу вверх", похожий на заполнение таблицы. Поскольку текущее состояние обычно зависит только от части локальных состояний, можно убрать одно измерение таблицы <span class="arithmatex">\(dp\)</span> и тем самым снизить пространственную сложность.</li>
|
||||
<li>Разложение на подзадачи - это общий алгоритмический подход, но в методе "разделяй и властвуй", динамическом программировании и поиске с возвратом он имеет разные свойства.</li>
|
||||
<li>Поиск с мемоизацией - это рекурсивный метод «сверху вниз», а соответствующее ему динамическое программирование - это итеративный метод «снизу вверх», похожий на заполнение таблицы. Поскольку текущее состояние обычно зависит только от части локальных состояний, можно убрать одно измерение таблицы <span class="arithmatex">\(dp\)</span> и тем самым снизить пространственную сложность.</li>
|
||||
<li>Разложение на подзадачи - это общий алгоритмический подход, но в методе «разделяй и властвуй», динамическом программировании и поиске с возвратом он имеет разные свойства.</li>
|
||||
<li>Для задач динамического программирования характерны три главных свойства: перекрывающиеся подзадачи, оптимальная подструктура и отсутствие последствий.</li>
|
||||
<li>Если оптимальное решение исходной задачи можно построить из оптимальных решений подзадач, то задача обладает оптимальной подструктурой.</li>
|
||||
<li>Отсутствие последствий означает, что для данного состояния его дальнейшее развитие определяется только этим состоянием и не зависит от всех прошлых состояний. Многие задачи комбинаторной оптимизации этим свойством не обладают и потому не могут эффективно решаться с помощью динамического программирования.</li>
|
||||
</ul>
|
||||
<p><strong>Задачи о рюкзаке</strong></p>
|
||||
<ul>
|
||||
<li>Задача о рюкзаке - один из самых типичных классов задач динамического программирования; она включает варианты 0-1 рюкзака, полного рюкзака, многократного рюкзака и другие.</li>
|
||||
<li>Задача о рюкзаке - один из самых типичных классов задач динамического программирования. Она включает варианты 0-1 рюкзака, полного рюкзака, многократного рюкзака и другие.</li>
|
||||
<li>В задаче о рюкзаке 0-1 состояние определяется как максимальная стоимость первых <span class="arithmatex">\(i\)</span> предметов в рюкзаке вместимости <span class="arithmatex">\(c\)</span> . Рассматривая два решения - не брать предмет и брать предмет, - можно получить оптимальную подструктуру и вывести уравнение перехода состояния. При оптимизации памяти, поскольку каждое состояние зависит от значения сверху и слева сверху, внутренний цикл нужно выполнять в обратном порядке, чтобы не перезаписать нужное значение.</li>
|
||||
<li>В задаче о полном рюкзаке число экземпляров каждого предмета не ограничено, поэтому при выборе предмета переход состояния отличается от варианта 0-1. Поскольку состояние зависит от значения сверху и слева, после оптимизации памяти внутренний цикл следует выполнять в прямом порядке.</li>
|
||||
<li>Задача о размене монет - это вариант задачи о полном рюкзаке. Здесь вместо "максимальной стоимости" ищется "минимальное число монет", поэтому в уравнении перехода <span class="arithmatex">\(\max()\)</span> заменяется на <span class="arithmatex">\(\min()\)</span> . Кроме того, вместо условия "не превышать вместимость рюкзака" нужно <strong>ровно</strong> набрать целевую сумму, поэтому значение <span class="arithmatex">\(amt + 1\)</span> используется как обозначение недопустимого решения "сумму набрать нельзя".</li>
|
||||
<li>В задаче о размене монет II вместо "минимального числа монет" требуется найти "число комбинаций монет", поэтому в уравнении перехода оператор <span class="arithmatex">\(\min()\)</span> заменяется на суммирование.</li>
|
||||
<li>Задача о размене монет - это вариант задачи о полном рюкзаке. Здесь вместо «максимальной стоимости» ищется «минимальное число монет», поэтому в уравнении перехода <span class="arithmatex">\(\max()\)</span> заменяется на <span class="arithmatex">\(\min()\)</span> . Кроме того, вместо условия «не превышать вместимость рюкзака» нужно <strong>ровно</strong> набрать целевую сумму, поэтому значение <span class="arithmatex">\(amt + 1\)</span> используется как обозначение недопустимого решения «сумму набрать нельзя».</li>
|
||||
<li>В задаче о размене монет II вместо «минимального числа монет» требуется найти «число комбинаций монет», поэтому в уравнении перехода оператор <span class="arithmatex">\(\min()\)</span> заменяется на суммирование.</li>
|
||||
</ul>
|
||||
<p><strong>Задача о расстоянии редактирования</strong></p>
|
||||
<ul>
|
||||
<li>Расстояние редактирования (расстояние Левенштейна) используется для измерения сходства двух строк и определяется как минимальное число операций редактирования, необходимых для преобразования одной строки в другую; допустимые операции - вставка, удаление и замена.</li>
|
||||
<li>Расстояние редактирования (расстояние Левенштейна) используется для измерения сходства двух строк и определяется как минимальное число операций редактирования, необходимых для преобразования одной строки в другую. Допустимые операции - вставка, удаление и замена.</li>
|
||||
<li>В задаче о расстоянии редактирования состояние определяется как минимальное число шагов редактирования, необходимых для преобразования первых <span class="arithmatex">\(i\)</span> символов строки <span class="arithmatex">\(s\)</span> в первые <span class="arithmatex">\(j\)</span> символов строки <span class="arithmatex">\(t\)</span> . Если <span class="arithmatex">\(s[i] \ne t[j]\)</span> , то существуют три решения: вставка, удаление и замена, и каждому из них соответствует своя остаточная подзадача. На этой основе выводятся оптимальная подструктура и уравнение перехода состояния. Если же <span class="arithmatex">\(s[i] = t[j]\)</span> , то редактировать текущий символ не нужно.</li>
|
||||
<li>В задаче о расстоянии редактирования состояние зависит от значений сверху, слева и слева сверху. Поэтому после оптимизации памяти ни прямой, ни обратный обход сам по себе не дает корректного перехода состояния. Для решения этой проблемы значение слева сверху временно сохраняется в отдельной переменной, что делает ситуацию эквивалентной задаче о полном рюкзаке и позволяет использовать прямой обход.</li>
|
||||
</ul>
|
||||
|
||||
Reference in New Issue
Block a user