记忆化搜索习题

本文介绍了记忆化搜索的使用条件,解释了为什么记忆化搜索比深度优先搜索(DFS)更高效,并通过三个实例——滑雪、老爷机和数字三角形问题,详细阐述了记忆化搜索的思路和教训,强调了在实现过程中判断点是否已访问的重要性。
摘要由CSDN通过智能技术生成

使用记忆化搜索的条件

  1. 最终状态dp值确定。
  2. 回溯可以确定其他dp值。

为什么记忆化搜索比dfs快

下图DFS,DE之间走了4次。反向箭头是回溯。
在这里插入图片描述
下图记忆化搜索,DE之间走了2次。因为在记忆化搜索中,一个点的dp值取决于他后边的点,dp[D]取决于dp[E],所以第二遍从另一条路线搜到D时,不用向E搜索了。
在这里插入图片描述

1. 滑雪

题意

每个点可以往上下左右,高度低于自己的位置走,求最长运动路径。

思路

最终状态dp值一定是上下左右走不了,为1。从该点回溯一定可以一次得到其他点的dp值,只要曾经访问过某点,他的dp值一定最优(证明见上边红色图片上边加粗字)。这里满足使用条件1和2,最终状态dp值为1,可以回溯确定其他值。

教训

一定要判断是否访问过某点,访问过直接return。理由同红图上方加粗字。

#include<iostream>
#include<cstdio>
#include<cstring>
using namespace std;
const int maxn = 1e4+10;
const int Next[4][2] = {
   {
   1,0},{
   -1,0},{
   0,1},{
   0,-1}};
typedef long long ll;
int hei[maxn][maxn];
int dp[maxn][maxn];
int n,m,nextx,nexty;

void init(){
   
    for(int i=1;i<=n;i++)
        for(int j=1;j<=m;j++)
            dp[i][j] = -1;
}

int dfs(int i,int j){
   
    if(dp[i][j] != -1)
        return dp[i][j];
    dp[i][j] = 1;
    for(int k=0;k<=3;k++){
   
        nextx = i + Next[k][0];
        nexty = j + Next[k][1];
        if(nextx>n||nextx<1||nexty>m||nexty<1||hei[nextx][nexty]>=hei[i][j])
            continue;
        dp[i][j] = max(dp[i][j
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值