uva11882 Biggest Number dfs搜索 剪很多枝

学习提速专享!AI工具全家桶免费用 限时购周边加赠Coding Plan Lite,解锁20+主流AI工具,写代码、查资料快人一步! 阅读详情

题目

奶奶的

有一天mirror58229提起一道dfs题
还是我们学校oj的,她说写的很麻烦
我就凑过去看,啊!这么标准的dfs究竟哪里会麻烦了呢?




于是就自己写了。。。
真的好麻烦啊!!!
TLE到WA到TLE。。。。
去网上搜题解都说要dfs走一步bfs一下,奶奶的好麻烦啊!!
我就是不想写bfs啊!!!
另外一个方法(当前结果已为最长,若此时搜索的第一个字比当前结果的第一个字小的话直接不搜)这个方法倒是不错,当然加进自己的代码后依旧超时
于是不干了
今晚mirror给了我数据,跑了一下还真的停慢的。。。
也知道自己wa哪里了。。。。
总之讲讲我的剪枝法吧:
1、先对输入的数字进行从大到小排序,若一个数字搜索完结果的长度是最大可能的话,就不继续搜比它更小的数字了
2、在dfs的过程中对当前的串进行比较,若到目前为止它已经比结果来得小也就不继续搜索了
反正这样剪剪就过了。。。。跑了320ms自己还以为挺快的
这里写图片描述
然后顺便搜了一下别人的情况。。。
这里写图片描述
天哪。。。。80ms的是怎么写出来的
简直是在做电子实验的时候才会用的单位吧。。。。
这里写图片描述
这里写图片描述
这里写图片描述
这里写图片描述
这里写图片描述
顺带一提这家伙好像是我开始做刘汝佳紫书的时候和我一起开始写的。。。。
因为每次我刷紫书的题的时候都会看到他在我附近的时间点提交的。。。。
刚开始的时候是差不多。。。。
有时提交完会发现几分钟前他也在提交
后来。。。。
然后发现他比我早了几天A。。。。
然后是早了几周A。。。。。。。。。
然后是早了几个月A。。。。。。。。。。
再之后就没有关注他了。。。
没想到会在今天再次看到这个id,居然已经刷到第七章了。。。。
哎。。。。膜拜之
贴一下这人的github和vj页面
github
vj
代码:

#include <iostream>
#include <cstring>
#include <cstdio>
#include <algorithm>
#include <cmath>
#include <stack>
using namespace std;
const int maxn = 45;
int dx[4] = {0,0,1,-1};
int dy[4] = {1,-1,0,0};
char now[maxn],res[maxn],save[16][16];
int r,c,p;
bool judge[maxn][maxn],flag;
bool compare(char *a,char *b){
    if(strlen(a)>strlen(b)){
        return true;
    }else if(strlen(a)<strlen(b)){
        return false;
    }else{
        int len = strlen(a),i;
        for(i=0;i<len;i++){
            if(a[i]>b[i]){
                return true;
            }else if(b[i]>a[i]){
                return false;
            }
        }
    }
    return false;
}
bool wtf(char *a,int len,char* b){
    int i;
    for(i=0;i<len;i++){
        if(a[i]>b[i]){
            return true;
        }else if(b[i]>a[i]){
            return false;
        }
    }
    return false;
}
void dfs(int x,int y){
    int i,len = (int)strlen(now)+1;
    if(flag&&wtf(res,len-1,now)){
        return;
    }
    now[len-1] = save[x][y];
    judge[x][y] = false;

    bool killme = true;
    for(i=0;i<4;i++){
        int nx =x+dx[i],ny = y+dy[i];
        if(nx>=1&&nx<=r&&ny>=1&&ny<=c&&judge[nx][ny]&&save[nx][ny]!='#'){
            dfs(nx, ny);
            killme = false;
        }
    }
    if(killme){
        if(compare(now, res)){
            memcpy(res,now,sizeof(now));
            if(len==p){
                flag = true;
            }
        }
    }
    now[len-1]='\0';
    judge[x][y] = true;
    return;
}
struct unit{
    pair<int, int> postion;
    int number;
};
bool comparePoint(unit a,unit b){
    return a.number>b.number;
}
unit point[maxn];
int main(){
    int i,j;
    while(~scanf("%d%d",&r,&c)){
        if(r==0&&c==0){
            break;
        }
        p=0;
        for(i=1;i<=r;i++){
            for(j=1;j<=c;j++){
                cin>>save[i][j];
                if(save[i][j]!='#'){
                    point[++p].postion = make_pair(i, j);
                    point[p].number = save[i][j] - '0';
                }
            }
        }
        res[0] = '\0';
        now[0] = '\0';
        flag = false;
        sort(point+1, point+1+p, comparePoint);
        point[0].number = point[1].number+1;
        for(i=1;i<=p;i++){
            memset(judge, true, sizeof(judge));
            if(flag&&point[i].number<point[i-1].number){
                break;
            }else{
                dfs(point[i].postion.first, point[i].postion.second);
            }
        }
        printf("%s\n",res);
    }

    return 0;
}
Uva11882 Biggest Numberdfs回溯+bfs】【习题7-15】 还是王道!!! 阅读详情

相关推荐

UVa 11882Biggest NumberDFS+

题目链接:https://uva.onlinejudge.org/index.php?option=com_onlinejudge&Itemid=8&category=842&page=show_problem&problem=3004 题意:在一个R行C列(2≤R,C≤15,R∗C≤30)(2 \le R, C \le 15, R*C \le 30 )的矩阵里有障碍物和数字格(包含1~9的数字

nullptr 1831

Biggest Number(回溯/bfs/)

Biggest Number - UVA 11882 - Virtual Judge (vjudge.net)寻找最大的数。dfs(回溯)+(bfs).由于string的大小比较和本题数字的大小比较类似,所以用string更方便。每一次dfs时要考虑当前节点之后所能串起来的,分为三种情况:1,太少,显然不满足,跳过当前的节点的dfs();2,+当前的长度now能跟之前一样长,那就比较ans的子字符串跟当前的now字符串谁大,如果ans大那就没必要继续();3,+当前now的长度比ans的长度更长

Crushlikearush的博客 284

UVA11882 Biggest Number

题目链接: UVA11882 解题思路: 常规思路是 枚举每个点,暴力dfs,然后选择最大的那个  但题目只给了1000MS 这就需要1: 假设当前答案长度为ans,那么当我们走到一个点(x, y)的时候,bfs一下判断能接触的格子数。假设现在能从(x, y)走到的点,我们都能到达,这是最好的情况。设从(x, y)能走到的点数为maxlen,那么如

旧时光 1587

11882 - Biggest Number ( 深搜 )

题目链接:传送门 思路: 以每个数字为起点去深搜,取在深搜过程中搜到的最大的 数。 注意, 如果只用蛮力去深搜会超时,所以需要需要用到广搜,就是你用深搜搜到某个点之后,先用广搜去计算 这个点继续深搜还能遍历所有的数字个数 a,假设现在Biggest Number 长度为 b, 搜到这个点已经深搜 的数的长度 c: 两种情况: 1. a+c < b 那么这个点...

学习笔记 976

Biggest Number深搜

Description You have a maze with obstacles and non-zero digits in it: You can start from any square, walk in the maze, and finally stop at some square. Each step, you may only walk into one of the four neighbouring squares (up, down, left, right) and you

PushyTao的博客 409

UVa 11882 最大的数(Biggest Number

题目链接:https://vjudge.net/problem/UVA-11882 大意是:搜索一下,连起来成为一个数字,不能反复走过一个格子,求最大的数字 思路: 本题搜索的话,会超时,需要搜索剩余可能步数,可以用bfs,基本在O(1)的时间就可以知道剩下几步可以走 #include<bits/stdc++.h> #define LL long long using names...

Inuyasha__的博客 433

C/C++ Biggest Number

题目描述 You have a maze with obstacles and non-zero digits in it: You can start from any square, walk in the maze, and finally stop at some square. Each step, you may only walk into one of the four n...

情不知所起,一往情深 538

uva11882 Biggest Number

UVA11882 这道题还是比较简单的,但是时间确实有点短 所以还是非常重要的,之前交过的代码都超时了,果然我还是个渣渣; 这里用到了一个非常简单的结构体node 函数ll有点像bfs 主要问题还是 如果已经走的长度加上还能走的最大长度小于ans(当前最优解)的长度,直接return; 如果以上两者长度相等,但是最优解的字典序大,return; 然后再比较当前最优解和目前的string s...

weixin_44578677的博客 192

UVa 11882 Biggest Number

本文探讨了在迷宫中寻找最大数字的路径搜索问题。题目要求从任意非障碍格子出发,在网格中移动(不重复访问且避开障碍物),将经过的数字连接起来形成最大数字。由于网格规模较小(R×C≤30),采用深度优先搜索(DFS)配合策略解题。

寂静山林 832

uva Biggest Number UVA - 11882 || nbut [1464] Biggest Number(dfs强力)

Biggest Number  UVA - 11882  数据较弱 题目大意:有一个R*C的矩阵,矩阵里面有1~9的数字(太好了不用处理前导0),或者是#(代表不能通过),先要从矩阵任意一点出发(之前英语抓鸡看成了边界,英语差的孩纸伤不起啊>_ 思路:DP?记忆化搜索?30个点噢,时间吃得消内存都吃不消啦。所以呢?搜索。还是超时啊?啊。 1:假设当前答案为ans,那么

MR CODER 272

UVA11882 Biggest Number

题目链接:http://acm.hust.edu.cn/vjudge/problem/viewProblem.action?id=23314 题意:给定一个方格,格子里或者是数字或者是'#'(即不能通过),问按照贪食蛇走法,按先后来排序,得到最大数字是什么(明显没有说清楚好嘛!) 思路:搜索。刚开始想到的只有DFS,超时。上网查题解才知道要用预判进行强力的。首先用长度进行预判,再在长度相等

beihai2013 569

uva 11882 Biggest Number

此题大意:给定一个矩阵,有些地方有数字,有些地方不能走,数字只包含1--9,现在问,可以从任意节点出发,将路径上的所有数字连在一起可以组成的最大的数是多少。 数据范围为 行数*列数 此题的第一眼想法就是直接dfs 但是 时间只有1s,直接dfs肯定会超时。 然后就是 方法:1.到达一个节点后对这个节点进行bfs,获得这个节点能够到达的节点数(num),当然在当前dfs

最爱她! 465

UVA 11882 Biggest Number搜索+dfs+bfs))

题意:在一个R行C列(2≤R,C≤15,R∗C≤30)的矩阵里有障碍物和数字格(包含1~9的数字)。你可以从任意一个数字格出发,每次沿着上下左右之一的方向走一格,但不能走到障碍格中,也不能重复经过一个数字格,然后把沿途经过的所有数字连起来,如图所示。如图可以得到9784,4832145等整数。问:能得到的最大整数是多少?(本段摘自《算法竞赛入门经典(第2版)》) 分析: 枚举起点

AK_HuangYC的博客 653

Uva 11882 Biggest Number (IDA*)

题目大意见紫书218。 一看到这道题第一反应就是dfs,然后第二反应就是单纯的dfs会T。。于是就考虑迭代加深。 首先预处理, 找到每个连通块的大小以及编号, maxd为当前寻找的数的位数,从1开始到最大连通块大小,于是对于障碍物 或者所在连通块大小小于maxd的数字格就不需要枚举了, 另外已经得到的数字如果已经小于的当前ans, 就直接return不需要继续找。 #include #in

zz_Black的博客 560

Biggest Number UVA - 11882

比较简单的一道搜索的题目,从有数字的位置开始,分别向上下左右四个方向进行搜索搜索的同时记录已经访问的数字串,并且记录当前已经使用的数字串的个数,计算出还可能使用的数字串的个数,如果两者之和小于已经保存的最优的结果的长度,那么就直接返回,如果长度相等,那么就对字符串进行比较,如果小于,那么也就直接返回。具体实现见如下代码: #include #include #include #include

zju2016的博客 306

习题 7-15 最大的数(Biggest Number, UVa11882

原题链接:https://vjudge.net/problem/UVA-11882 分类:迭代 备注:A*算法 利用剩余可能的最大长度判断一下是否继续搜,如果当前长度加上这个长度后等于目前答案长度,比较一下当前值和答案前缀。 #include<bits/stdc++.h> using namespace std; const int dir[][2]={{0,1},{1,0},{-1,0},{0,-1}}; int row,col,vis[20][20],len[20][20]; char

TK_wang_的博客 312

UVA 11882(p218)----Biggest Number

#include #include #include #include #include using namespace std; typedef long long LL; const int maxn=33; struct node { int a[maxn],len; void cl() { len=0; } void print

哆啦AC梦的博客 350

搜索+强UVA-11882 - Biggest Number

处理得很巧妙的DFS+BFS…… 题目 #include #include #include using namespace std; #define FRE freopen("a.txt","r",stdin); struct node { int x,y; }queue[1000]; int n,m; int Max,flag,tatal; char map[20][20];

AndRing的专栏 2054
上一篇: poj2632 Crashing Robots 模拟
下一篇: hhu1017 最小差 动态规划dp 01背包
kyoma
博客等级 码龄10年 28粉丝 226原创
评论
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符
 
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值