답안 #914710

# 제출 시각 아이디 문제 언어 결과 실행 시간 메모리
914710 2024-01-22T15:00:51 Z qin Furniture (JOI20_furniture) C++17
0 / 100
2 ms 604 KB
#include <bits/stdc++.h>
#define fi first
#define se second
#define ssize(x) int(x.size())
#define pn printf("\n");
#define all(x) x.begin(),x.end()
#define rall(x) x.rbegin(),x.rend()
#define vv vector
using namespace std;
typedef long long ll;
typedef pair<int, int> pii;
int inf = 2e09; ll infll = 2e18; int mod = 119<<23|1;
void bfs_up(vv<vv<int>> &t, vv<vv<int>> &ed, pii st, vv<set<int>> &s){
		queue<pii> q;
		if(!t[st.fi-1][st.se]) q.emplace(pii(st.fi-1, st.se));
		if(!t[st.fi][st.se-1]) q.emplace(pii(st.fi, st.se-1));
		while(!q.empty()){
				int i = q.front().fi, j = q.front().se; q.pop();
				if(!t[i+1][j] || !t[i][j+1]) continue; // nie musimy usuwać, bo jest przejście
				t[i][j] = 1;
				
				auto it = prev(s[i].upper_bound(j)); // modyfikuję seta, nie sądzę, że muszę sprawdzać czy begin
				if(*it == j) s[i].erase(it);
				else ed[i][*it] = j-1;
				
				if(!t[i-1][j]) q.emplace(pii(i-1, j));
				if(!t[i][j-1]) q.emplace(pii(i, j-1));
		}
}
void bfs_down(vv<vv<int>> &t, vv<vv<int>> &ed, pii st, vv<set<int>> &s){
		queue<pii> q;
		if(!t[st.fi+1][st.se]) q.emplace(pii(st.fi+1, st.se));
		if(!t[st.fi][st.se+1]) q.emplace(pii(st.fi, st.se+1));
		while(!q.empty()){
				int i = q.front().fi, j = q.front().se; q.pop();
				//~ printf("%d %d\n", i, j);
				if(!t[i-1][j] || !t[i][j-1]) continue; // nie musimy usuwać, bo jest przejście
				t[i][j] = 1;
				
				auto it = s[i].lower_bound(j); // modyfikuję seta
				assert(it != s[i].end());
				if(ed[i][*it] == j) s[i].erase(it);
				else{ int tmp = *it; ed[i][*it+1] = ed[i][*it], ed[i][*it] = 0, s[i].erase(it), s[i].emplace(tmp+1); }
				
				if(!t[i+1][j]) q.emplace(pii(i+1, j));
				if(!t[i][j+1]) q.emplace(pii(i, j+1));
		}
}
void answer(){
		int n, m; scanf("%d%d", &n, &m);
		vv<vv<int>> t(n+2, vv<int>(m+2, 0)), ed(n+2, vv<int>(m+2, 0)); // w e trzymam koniec przedziału, ktory jest na secie
		vector<pii> red;
		for(int i = 1; i <= n; ++i)
				for(int j = 1, a; j <= m; ++j){ scanf("%d", &a); if(a) red.emplace_back(i, j); }
		
		for(int i = 1; i <= n; ++i) t[i][0] = 1, t[i][m+1] = 1; // narożników chyba nie muszę, ale kto wie, zostawiam komentarz
		for(int j = 1; j <= m; ++j) t[0][j] = 1, t[n+1][j] = 1;
		
		vv<set<int>> s(n+2);
		for(int i = 1; i <= n; ++i) s[i].emplace(1), ed[i][1] = m;
		
		for(pii &u : red){
				int i = u.fi, j = u.se;
				if(t[i][j]) continue;
				auto it = prev(s[i].upper_bound(j));
				if(ed[i][*it] != j) ed[i][j+1] = ed[i][*it], s[i].emplace(j+1);
				it = prev(s[i].upper_bound(j));
				if(*it != j) ed[i][*it] = j-1;
				else s[i].erase(it); 
				t[i][j] = 1;
				bfs_up(t, ed, pii(i, j), s), bfs_down(t, ed, pii(i, j), s);
				//~ pn;
				//~ for(i = 1; i <= n; ++i){
						//~ for(j = 1; j <= m; ++j) printf("%d ", t[i][j]);
						//~ pn;
				//~ }
				//~ for(i = 1; i <= n; ++i){
						//~ for(int x : s[i]) printf("%d %d, ", x, ed[i][x]);
						//~ pn;
				//~ }
		}
		int q; scanf("%d", &q);
		for(++q; --q; ){
				int i, j; scanf("%d%d", &i, &j);
				if(t[i][j]){ printf("1\n"); continue; }
				if(ssize(s[i]) > 1){
						printf("1\n");
						auto it = prev(s[i].upper_bound(j));
						if(ed[i][*it] != j) ed[i][j+1] = ed[i][*it], s[i].emplace(j+1);
						it = prev(s[i].upper_bound(j));
						if(*it != j) ed[i][*it] = j-1;
						else s[i].erase(it); 
						t[i][j] = 1;
						bfs_up(t, ed, pii(i, j), s), bfs_down(t, ed, pii(i, j), s);
						continue;
				}
				
				bool left = 1, right = 1;
				auto it = prev(s[i].upper_bound(j));
				int it_beg = *it, it_ed = ed[i][*it];
				if(*it == j) left = 0;
				if(it_ed == j) right = 0;
				//~ printf("a\n");
				if(right){
						bool good = 0;
						it = s[i-1].lower_bound(j+1);
						if(it != s[i-1].end() && *it <= it_ed) good = 1;
						if(it != s[i-1].begin() && j+1 <= ed[i-1][*prev(it)]) good = 1;
						if(!good) right = 0;
				}
				//~ printf("b\n");
				if(left){
						bool good = 0;
						//~ printf("%d\n", it_beg);
						it = s[i+1].lower_bound(it_beg);
						//~ printf("%d\n", it_beg);
						if(it != s[i+1].end() && *it <= j-1) good = 1;
						if(it != s[i+1].begin() && it_beg <= ed[i+1][*prev(it)]) good = 1;
						if(!good) left = 0;
				}
				//~ printf("%d %d\n", int(left), int(right));
				if(!left && !right) printf("0\n");
				else{
						printf("1\n");
						it = prev(s[i].upper_bound(j));
						if(ed[i][*it] != j) ed[i][j+1] = ed[i][*it], s[i].emplace(j+1);
						it = prev(s[i].upper_bound(j));
						if(*it != j) ed[i][*it] = j-1;
						else s[i].erase(it); 
						t[i][j] = 1;
						bfs_up(t, ed, pii(i, j), s), bfs_down(t, ed, pii(i, j), s);
				}
		}
}
int main(){
		int T = 1;
		for(++T; --T; ) answer();
		return 0;
}

Compilation message

furniture.cpp: In function 'void answer()':
furniture.cpp:50:18: warning: ignoring return value of 'int scanf(const char*, ...)' declared with attribute 'warn_unused_result' [-Wunused-result]
   50 |   int n, m; scanf("%d%d", &n, &m);
      |             ~~~~~^~~~~~~~~~~~~~~~
furniture.cpp:54:42: warning: ignoring return value of 'int scanf(const char*, ...)' declared with attribute 'warn_unused_result' [-Wunused-result]
   54 |     for(int j = 1, a; j <= m; ++j){ scanf("%d", &a); if(a) red.emplace_back(i, j); }
      |                                     ~~~~~^~~~~~~~~~
furniture.cpp:82:15: warning: ignoring return value of 'int scanf(const char*, ...)' declared with attribute 'warn_unused_result' [-Wunused-result]
   82 |   int q; scanf("%d", &q);
      |          ~~~~~^~~~~~~~~~
furniture.cpp:84:20: warning: ignoring return value of 'int scanf(const char*, ...)' declared with attribute 'warn_unused_result' [-Wunused-result]
   84 |     int i, j; scanf("%d%d", &i, &j);
      |               ~~~~~^~~~~~~~~~~~~~~~
# 결과 실행 시간 메모리 Grader output
1 Runtime error 2 ms 604 KB Execution killed with signal 6
2 Halted 0 ms 0 KB -
# 결과 실행 시간 메모리 Grader output
1 Runtime error 2 ms 604 KB Execution killed with signal 6
2 Halted 0 ms 0 KB -