识海社区打卡-4

今天打卡大模拟

Problem - 1365D - Codeforces

image-20241113234004941

大模拟确实恶心人,但作为最臭的屎平时还是得多吃点,大模拟的特点是思路不算很难但代码真的很长很长,一个不小心哪里写得有问题查错就是半天,各种细节都要很注意,对于提升自己查错能力和快速写题能力还是很有帮助的,这种屎虽然恶心但是就是得多吃。

简单说下题意,大概就是给定一个网格图,网格图有四种符号,#代表墙,B代表bad坏人,G代表good好人, "."代表空白,可以把一些空白变成墙,然后使所有好人能跑走,坏人留下,并且只有跑到[n,m]才算逃出生天。

思路很简单,就是把所有坏人都关起来,好人不能和坏人相邻,并且好人没有被关起来的。

代码实现

#include <bits/stdc++.h>
using namespace std;
const char nl = '\n';
#define all(x) (x).begin(), (x).end()
typedef long long ll;
typedef long double ld;
typedef long long int lli;
const int MOD = 1'000'000'007;
constexpr int inf = 1e9;

constexpr int dx[] = {0, 0, -1, 1}, dy[] = {-1, 1, 0, 0};

void solve()
{
  int n, m;
  cin >> n >> m;
  vector<string> a(n);
  int res = 0;
  for (int i = 0; i < n; i++)
  {
    cin >> a[i];
    res += count(a[i].begin(), a[i].end(), 'G');
  }
  if (res == 0)
  {
    cout << "YES" << nl;
    return;
  }
  a[n - 1][m - 1] = 'G';
  for (int i = 0; i < n; i++)
  {
    for (int j = 0; j < m; j++)
    {
      if (a[i][j] == 'B')
      {
        for (int k = 0; k < 4; k++)
        {
          int x = j + dx[k], y = i + dy[k];
          if (x < m && x >= 0 && y >= 0 && y < n)
          {
            if (a[y][x] == 'G')
            {
               cout << "NO" << nl;
              return;
            }
            if (a[y][x] == '.')
            {
              a[y][x] = '#';
            }
          }
        }
      }
    }
  }

  vector<vector<bool>> vis(n, vector<bool>(m));
  queue<pair<int, int>> q;
  vis[n - 1][m - 1] = 1;
  q.emplace(n - 1, m - 1);
  while (!q.empty())
  {
    auto [i, j] = q.front();
    q.pop();
    for (int k = 0; k < 4; ++k)
    {
      int x = i + dx[k], y = j + dy[k];
      if (0 <= x && x < n && 0 <= y && y < m && a[x][y] != '#' && !vis[x][y])
      {
        
        vis[x][y] = true;
        q.emplace(x, y);
      }
    }
  }

  for(int i = 0;i < n;i++){
    for(int j = 0;j < m;j++){
      if(a[i][j] == 'G' && !vis[i][j]){
        cout << "NO" << nl;
        return;
      }
    }
  }
 
  cout << "YES" << nl;
}

int main()
{
  ios::sync_with_stdio(0), cin.tie(0), cout.tie(0);
  int t = 1;
  cin >> t;
  while (t--)
  {
    solve();
  }
  return 0;
}

代码的思路就是先查找有没有好人,如果没有就直接把出口堵上就好了所以肯定是yes因为题目保证了出口是空白

其次是把最后的位置变为一个好人,因为当好人和坏人分别在出口的上方和左方时是不行的,直接把这种情况算到好人和坏人相邻就行,然后查找好人与坏人相邻的情况,并且把所有坏人都关上。

最后是从出口开始查找对于所有通出口的地方都标记为1,所有不通的地方都标为0,然后查找好人被关的情况就行。

posted @   夏尾草  阅读(5)  评论(0编辑  收藏  举报
相关博文:
阅读排行:
· winform 绘制太阳,地球,月球 运作规律
· AI与.NET技术实操系列(五):向量存储与相似性搜索在 .NET 中的实现
· 超详细:普通电脑也行Windows部署deepseek R1训练数据并当服务器共享给他人
· 【硬核科普】Trae如何「偷看」你的代码?零基础破解AI编程运行原理
· 上周热点回顾(3.3-3.9)
点击右上角即可分享
微信分享提示