1. 전부 입력받는다 (바이러스는 기본적으로 비활성화 시킨 상태로 저장)
2. 입력받은 바이러스 중 m개의 바이러스를 뽑는다.
3. 다 뽑았으면 바이러스를 새로운 지도에 퍼뜨려본다.
4. 새로운 지도에 바이러스가 다 퍼질 때까지의 최소시간을 구한다.
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 | #include<iostream> #include<queue> #include<vector> #include<utility> #include<algorithm> using namespace std; #define endl "\n" #define space " " #define MAX 99999999 int dx[]={0,0,1,-1}, dy[]={1,-1,0,0}; struct data{int y,x;}; queue<struct data> q; vector<pair<int,int>> virus; // 모든 바이러스 vector<pair<int,int>> virus_pos; // 뽑은 바이러스 int arr[52][52]; // 입력받은 지도 int map[52][52]; // 바이러스 퍼뜨릴 지도 bool visited[12]; // 바이러스 뽑는 용도 int n,m,x,y,ans=MAX,temp,cnt; void copy_map(){ for(int i=0; i<n; i++) for(int j=0; j<n; j++) map[i][j]=arr[i][j]; } int spread(){ temp=0; while(!q.empty()){ y=q.front().y; x=q.front().x; q.pop(); for(int k=0; k<4; k++){ int nx=x+dx[k]; int ny=y+dy[k]; if(0<=nx && nx<n && 0<=ny && ny<n){ if(arr[ny][nx]==0 && map[ny][nx]==0){ q.push({ny,nx}); map[ny][nx]=map[y][x]+1; } // 비활성화 바이러스라도 일단 퍼뜨려보자 if(arr[ny][nx]==-2 && map[ny][nx]==-2){ q.push({ny,nx}); map[ny][nx]=map[y][x]+1; } } } } for(int i=0; i<n; i++){ for(int j=0; j<n; j++){ cout << map[i][j] << space ; // 아직 빈공간이면 틀린거임 if(map[i][j]==0){ return MAX; } // 처음 입력 받아을 때 빈공간이었던 자리 중에서 최소시간 else if(temp<map[i][j] && arr[i][j]==0) temp=map[i][j]; } } return temp; } void func(int cur, int cnt){ if(cnt==m){ copy_map(); // 지도 복사 // m개만큼 뽑은 바이러스를 큐에 넣기 for(int i=0; i<virus_pos.size(); i++){ map[virus_pos[i].first][virus_pos[i].second]=1; q.push({virus_pos[i].first, virus_pos[i].second}); } // 큐에 넣은 후에 최소시간 고르기 cnt=spread(); ans=min(ans,cnt); return; } // 바이러스 고르기 for(int i=cur; i<virus.size(); i++){ if(!visited[i]){ visited[i]=true; virus_pos.push_back(make_pair(virus[i].first, virus[i].second)); func(i+1,cnt+1); visited[i]=false; virus_pos.pop_back(); } } } int main(void){ cin >> n >> m; for(int i=0; i<n; i++){ for(int j=0; j<n; j++){ cin >> arr[i][j]; if(arr[i][j]==2){ virus.push_back(make_pair(i,j)); arr[i][j]=-2; // 기본적으로 바이러스 비활성화 } else if(arr[i][j]==1) arr[i][j]=-1; // 벽 } } func(0,0); if (ans==MAX) cout << "-1"; else if (ans==0) cout << "0"; else cout << ans-1; return 0; } | cs |
'백준 2 > 완전탐색' 카테고리의 다른 글
| [백준 18808] 스티커 붙이기 (C++/Python) (0) | 2023.09.11 |
|---|---|
| [백준 15683] 감시 (C++/Python) (0) | 2023.09.09 |
| [백준 14225] 부분수열의 합 (0) | 2020.12.07 |
| [백준 7568] 덩치 (0) | 2020.12.07 |
| [백준 1018] 체스판 칠하기 (C++/Python) (0) | 2020.12.07 |