• POJ3009 Curling 2.0


    http://poj.org/problem?id=3009

    扔冰球

    最开始没看懂示例数据 才发现相邻有墙时不能扔

    程序一定要有很好的可读性 要说清楚 不然越改越烦

    具体思路:

    每撞到墙 墙体会消失 地图在发生改变 所以不能广搜

    深度+回溯

    因为深搜会搜出所有可能的投掷方案 所以step <= 10作为剪枝

    每一个格子有4种方向 4^10 = 10^6绰绰有余

    选择一个方向投掷 检测是否越界 检测是否可以投掷 检测是否到终点---->>>.更新终点步数

    继续搜索的情况---->>>撞到墙壁 ->击碎墙壁->继续搜索->回溯->修复墙壁->下一个方向

    //终于在看了别人的代码后过了 这种混了模拟的题 一定不要慌 不要一堆条件
    //条理is so important 不然就要找bug找死(流程图first)
    //写得越简单越好 越清晰越好 god!!

     1 #include <iostream>
     2 #include <stdio.h>
     3 
     4 using namespace std;
     5 
     6 const int INF = 0x3f3f3f3f;
     7 int N,M;
     8 int goal = INF;
     9 int board[25][25];
    10 int d[4][2] = { {-1, 0}, {0, 1}, {1, 0}, {0, -1} };
    11 int sx,sy,ex,ey;
    12 
    13 
    14 bool check(int x, int y)//检查是否越界
    15 {
    16     if (x < 0 || y < 0 || x >= M || y >= N) return false;
    17     return true;
    18 }
    19 
    20 void dfs(int step, int x, int y)
    21 {
    22     int nx, ny;
    23     if (step > 10) return ;//剪枝
    24     for (int i = 0; i < 4; i++)
    25     {
    26         nx = x + d[i][0];
    27         ny = y + d[i][1];
    28         if (!check(nx,ny)) continue;//越界
    29         if(board[nx][ny] == 1) continue;//直接遇到墙了
    30         while (!board[nx][ny])
    31         {
    32             nx += d[i][0];
    33             ny += d[i][1];
    34             if (!check(nx,ny)) break;//如果越界就退出
    35         }
    36         if (check(nx,ny))//如果没有越界
    37         {
    38             if (board[nx][ny] == 3)//如果到终点了
    39             {
    40                 goal = min(goal, step);
    41             }
    42             if (board[nx][ny] == 1)
    43             {
    44                 board[nx][ny] = 0;//击碎岩石
    45                 dfs(step+1, nx-d[i][0], ny-d[i][1]);
    46                 board[nx][ny] = 1;//回溯修复岩石
    47             }
    48         }
    49     }
    50 }
    51 
    52 int main()
    53 {
    54     freopen("in.txt", "r", stdin);
    55     while ( ~scanf("%d%d", &N, &M) )
    56     {
    57         if (M == 0 && N == 0)   break;
    58         for(int i = 0; i < M; i++)
    59         {
    60             for (int j = 0; j < N; j++)
    61             {
    62                 scanf( "%d", &board[i][j] );
    63                 if (board[i][j] == 2)
    64                 {
    65                     sx = i;
    66                     sy = j;
    67                     board[i][j] = 0;
    68                 }//起点就是一个起始的地方和0没有区别
    69                 if (board[i][j] == 3)
    70                 {
    71                     ex = i;
    72                     ey = j;
    73                 }
    74             }
    75         }
    76         goal = INF;
    77         dfs(1, sx, sy);
    78         if (goal != INF) printf("%d
    ", goal);
    79         else printf("-1
    ");
    80     }
    81     return 0;
    82 }
  • 相关阅读:
    Git 分支[转]
    监听键盘的输入事件[转]
    github for windows的初步使用
    限制一个form被同时打开的数量 Limite The Number of Forms Opened at the same time
    android内存检测工具
    面试 9.26 总结
    canvas path paint 的使用(游戏必备)
    android知识点
    android查缺补漏
    AIDL的使用
  • 原文地址:https://www.cnblogs.com/oscar-cnblogs/p/6295111.html
Copyright © 2020-2023  润新知