[230330][白俊/BOJ]10026号赤色薬


質問する



にゅうしゅつりょく



に答える


赤緑薬とは赤と緑の区別がつかない人のこと.
まず、非赤色薬の人が本領域にいる個数を求め、その後、赤色を緑色に変え、その後、赤色薬を出力した人が見た領域の個数を求める.vis配列を初期化するだけで、最初の領域を出力してアクセスしたかどうかの数を簡単に解決できます.

コード#コード#

#include <bits/stdc++.h>
using namespace std;
#define X first
#define Y second
#define SIZE 102

char board[SIZE][SIZE];
bool vis[SIZE][SIZE];

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

int main()
{
	ios::sync_with_stdio(0);
	cin.tie(0);	
	
	int n, tc = 2;
	cin >> n;

	for (int i = 0; i < n; ++i)
		for (int j = 0; j < n; ++j)
			cin >> board[i][j];

	while (tc--) // 적록색약이 아닌 경우와 적록색약인 경우 
	{
		int cnt = 0; // 영역의 개수 
		for (int i = 0; i < n; ++i)
		{
			for (int j = 0; j < n; ++j)
			{
				if (vis[i][j]) continue;
				queue<pair<int, int>> Q;
				Q.push({ i,j });
				vis[i][j] = 1;
				char c = board[i][j]; // 구역 비교하기 위해
				cnt++;

				while (!Q.empty())
				{
					auto cur = Q.front(); Q.pop();
					for (int dir = 0; dir < 4; ++dir)
					{
						int nx = cur.X + dx[dir];
						int ny = cur.Y + dy[dir];
						if (nx < 0 || nx >= n || ny < 0 || ny >= n)continue;
						if (vis[nx][ny] || board[nx][ny] != c) continue;
						Q.push({ nx,ny });
						vis[nx][ny] = 1;
					}
				}
			}
		}
		cout << cnt << '\n';

		fill(vis[0], vis[0] + SIZE * SIZE, 0); // 적록색약인 경우 계산하기 위해 초기화
		
		for (int i = 0; i < n; ++i)
			for (int j = 0; j < n; ++j)
				if (board[i][j] == 'R') // 빨간색이면
					board[i][j] = 'G'; // 초록색으로 변경
	}
}