• BFS专题9 中国象棋-马-有障碍


    题目:

    思路:

            由题意,这也是 BFS 即可,这里注意的是,我们要存储好哪些坐标有障碍,在搜索各个方向的时候,判断搜索的对应方向是否有障碍,即  !r[tem.x + dx[i] / 2][tem.y + dy[i] / 2]

    代码详解如下:

    1. #include
    2. #include
    3. #include
    4. #include
    5. #include
    6. #include
    7. #define endl '\n'
    8. #define x first
    9. #define y second
    10. #define mk make_pair
    11. #define YES puts("YES")
    12. #define NO puts("NO")
    13. #define umap unordered_map
    14. #define All(x) x.begin(),x.end()
    15. #pragma GCC optimize(3,"Ofast","inline")
    16. #define IOS std::ios::sync_with_stdio(false),cin.tie(0), cout.tie(0)
    17. using namespace std;
    18. const int N = 500;
    19. using PII = pair<int,int>;
    20. // 象棋走动的方向
    21. int dx[8] = {2,2,-2,-2,1,-1,1,-1};
    22. int dy[8] = {1,-1,1,-1,2,2,-2,-2};
    23. int g[N][N],n,m; // 象棋棋盘以及大小
    24. bool st[N][N]; // 标记是否走过当前坐标
    25. bool r[N][N]; // 记录障碍坐标
    26. int k;
    27. PII now; // 当前象棋坐标
    28. // 走动条件的判断
    29. inline bool isRun(int &x,int &y)
    30. {
    31. // 且当前坐标 r 没有障碍的时候 返回 true
    32. return (x > 0 && x <= n && y > 0 && y <= m && !st[x][y] && !r[x][y]);
    33. }
    34. inline void BFS()
    35. {
    36. // 初始化坐标所对应的最少步数
    37. memset(g,-1,sizeof g);
    38. g[now.x][now.y] = 0; // 初始化起点步数为 0
    39. int step = 0;
    40. queueq;
    41. q.emplace(now);
    42. while(q.size())
    43. {
    44. int sz = q.size();
    45. while(sz--)
    46. {
    47. PII tem = q.front();
    48. q.pop(); // 取出当前坐标
    49. st[tem.x][tem.y] = true; // 标记当前坐标
    50. g[tem.x][tem.y] = step; // 存储当前坐标所对应的最少步数
    51. // 尝试往各个方向坐标走动
    52. for(int i = 0;i < 8;++i)
    53. {
    54. int bx = tem.x + dx[i];
    55. int by = tem.y + dy[i];
    56. // 如果符合走动条件,且对应方向的前一个坐标没有障碍那么可以走动
    57. if(isRun(bx,by) && !r[tem.x + dx[i] / 2][tem.y + dy[i] / 2])
    58. {
    59. // 如果符合走动条件
    60. // 存储下一个走动的坐标,并标记
    61. q.emplace(mk(bx,by));
    62. st[bx][by] = true;
    63. }
    64. }
    65. }
    66. ++step;
    67. }
    68. }
    69. // 打印棋盘各个坐标所对应的最少步数
    70. inline void PrintG()
    71. {
    72. for(int i = 1;i <= n;++i)
    73. {
    74. for(int j = 1;j <= m;++j)
    75. {
    76. if(j > 1) cout << ' '; // 控制输入格式
    77. cout << g[i][j];
    78. }
    79. cout << endl;
    80. }
    81. }
    82. inline void solve()
    83. {
    84. cin >> n >> m >> now.x >> now.y >> k; // 输入所对应的信息
    85. // 输入有障碍坐标
    86. while(k--)
    87. {
    88. int x,y;
    89. cin >> x >> y;
    90. r[x][y] = true; // 标记
    91. }
    92. BFS(); // BFS 搜索各个坐标所对应的最少步数
    93. PrintG(); // 输出答案
    94. }
    95. int main()
    96. {
    97. // freopen("a.txt", "r", stdin);
    98. IOS;
    99. int _t = 1;
    100. // cin >> _t;
    101. while (_t--)
    102. {
    103. solve();
    104. }
    105. return 0;
    106. }

    最后提交:

  • 相关阅读:
    C++项目实战——基于多设计模式下的同步&异步日志系统-⑪-日志器管理类与全局建造者类设计(单例模式)
    【前端攻城师之JS基础】03函数进阶
    C++的Odyssey之旅——STL
    前端工程化02-复习jQuery当中的插件开发
    Day13--搜索历史-清空搜索历史记录
    计算机毕业设计 SSM养老院管理系统 智慧养老院管理系统 养老院信息管理系统Java Vue MySQL数据库 远程调试 代码讲解
    【附源码】Python计算机毕业设计万达影院售票管理系统
    猿创征文|[云原生] docker查看日志用法笔记
    作业练习2:类与数据结构
    初探CSS 上
  • 原文地址:https://blog.csdn.net/hacker_51/article/details/133968081