fork download
  1. #include <bits/stdc++.h>
  2. using namespace std;
  3.  
  4. typedef long long ll;
  5. typedef long double ld;
  6. typedef double db;
  7. typedef string str;
  8.  
  9. typedef pair<int,int> pi;
  10. typedef pair<ll,ll> pl;
  11. typedef pair<db,db> pd;
  12.  
  13. typedef vector<int> vi;
  14. typedef vector<ll> vl;
  15. typedef vector<db> vd;
  16. typedef vector<str> vs;
  17. typedef vector<pi> vpi;
  18. typedef vector<pl> vpl;
  19. typedef vector<pd> vpd;
  20.  
  21. #define mp make_pair
  22. #define f first
  23. #define s second
  24. #define sz(x) (int)(x).size()
  25. #define all(x) begin(x), end(x)
  26. #define rall(x) (x).rbegin(), (x).rend()
  27. #define rsz resize
  28. #define ins insert
  29. #define ft front()
  30. #define bk back()
  31. #define pf push_front
  32. #define pb push_back
  33. #define eb emplace_back
  34. #define lb lower_bound
  35. #define ub upper_bound
  36.  
  37. #define FOR(i,a,b) for (int i = (a); i < (b); ++i)
  38. #define F0R(i,a) FOR(i,0,a)
  39. #define ROF(i,a,b) for (int i = (b)-1; i >= (a); --i)
  40. #define R0F(i,a) ROF(i,0,a)
  41. #define trav(a,x) for (auto& a: x)
  42.  
  43. const int MOD = 1e9+7; // 998244353;
  44. const int MX = 2e5+5;
  45. const ll INF = 1e18;
  46. const ld PI = acos((ld)-1);
  47. const int xd[4] = {1,0,-1,0}, yd[4] = {0,1,0,-1};
  48. mt19937 rng((uint32_t)chrono::steady_clock::now().time_since_epoch().count());
  49.  
  50. template<class T> bool ckmin(T& a, const T& b) {
  51. return b < a ? a = b, 1 : 0; }
  52. template<class T> bool ckmax(T& a, const T& b) {
  53. return a < b ? a = b, 1 : 0; }
  54. constexpr int pct(int x) { return __builtin_popcount(x); }
  55. constexpr int bits(int x) { return 31-__builtin_clz(x); } // floor(log2(x))
  56. ll cdiv(ll a, ll b) { return a/b+((a^b)>0&&a%b); } // divide a by b rounded up
  57. ll fdiv(ll a, ll b) { return a/b-((a^b)<0&&a%b); } // divide a by b rounded down
  58. ll half(ll x) { return fdiv(x,2); }
  59.  
  60. template<class T, class U> T fstTrue(T lo, T hi, U f) {
  61. hi ++; assert(lo <= hi); // assuming f is increasing
  62. while (lo < hi) { // find first index such that f is true
  63. T mid = half(lo+hi);
  64. f(mid) ? hi = mid : lo = mid+1;
  65. }
  66. return lo;
  67. }
  68. template<class T, class U> T lstTrue(T lo, T hi, U f) {
  69. lo --; assert(lo <= hi); // assuming f is decreasing
  70. while (lo < hi) { // find first index such that f is true
  71. T mid = half(lo+hi+1);
  72. f(mid) ? lo = mid : hi = mid-1;
  73. }
  74. return lo;
  75. }
  76. template<class T> void remDup(vector<T>& v) {
  77. sort(all(v)); v.erase(unique(all(v)),end(v)); }
  78.  
  79. // INPUT
  80. template<class A> void re(complex<A>& c);
  81. template<class A, class B> void re(pair<A,B>& p);
  82. template<class A> void re(vector<A>& v);
  83. template<class A, size_t SZ> void re(array<A,SZ>& a);
  84.  
  85. template<class T> void re(T& x) { cin >> x; }
  86. void re(db& d) { str t; re(t); d = stod(t); }
  87. void re(ld& d) { str t; re(t); d = stold(t); }
  88. template<class H, class... T> void re(H& h, T&... t) { re(h); re(t...); }
  89.  
  90. template<class A> void re(complex<A>& c) { A a,b; re(a,b); c = {a,b}; }
  91. template<class A, class B> void re(pair<A,B>& p) { re(p.f,p.s); }
  92. template<class A> void re(vector<A>& x) { trav(a,x) re(a); }
  93. template<class A, size_t SZ> void re(array<A,SZ>& x) { trav(a,x) re(a); }
  94.  
  95. // TO_STRING
  96. #define ts to_string
  97. str ts(char c) { return str(1,c); }
  98. str ts(const char* s) { return (str)s; }
  99. str ts(str s) { return s; }
  100. str ts(bool b) {
  101. #ifdef LOCAL
  102. return b ? "true" : "false";
  103. #else
  104. return ts((int)b);
  105. #endif
  106. }
  107. template<class A> str ts(complex<A> c) {
  108. stringstream ss; ss << c; return ss.str(); }
  109. str ts(vector<bool> v) {
  110. str res = "{"; F0R(i,sz(v)) res += char('0'+v[i]);
  111. res += "}"; return res; }
  112. template<size_t SZ> str ts(bitset<SZ> b) {
  113. str res = ""; F0R(i,SZ) res += char('0'+b[i]);
  114. return res; }
  115. template<class A, class B> str ts(pair<A,B> p);
  116. template<class T> str ts(T v) { // containers with begin(), end()
  117. #ifdef LOCAL
  118. bool fst = 1; str res = "{";
  119. for (const auto& x: v) {
  120. if (!fst) res += ", ";
  121. fst = 0; res += ts(x);
  122. }
  123. res += "}"; return res;
  124. #else
  125. bool fst = 1; str res = "";
  126. for (const auto& x: v) {
  127. if (!fst) res += " ";
  128. fst = 0; res += ts(x);
  129. }
  130. return res;
  131.  
  132. #endif
  133. }
  134. template<class A, class B> str ts(pair<A,B> p) {
  135. #ifdef LOCAL
  136. return "("+ts(p.f)+", "+ts(p.s)+")";
  137. #else
  138. return ts(p.f)+" "+ts(p.s);
  139. #endif
  140. }
  141.  
  142. // OUTPUT
  143. template<class A> void pr(A x) { cout << ts(x); }
  144. template<class H, class... T> void pr(const H& h, const T&... t) {
  145. pr(h); pr(t...); }
  146. void ps() { pr("\n"); } // print w/ spaces
  147. template<class H, class... T> void ps(const H& h, const T&... t) {
  148. pr(h); if (sizeof...(t)) pr(" "); ps(t...); }
  149.  
  150. // DEBUG
  151. void DBG() { cerr << "]" << endl; }
  152. template<class H, class... T> void DBG(H h, T... t) {
  153. cerr << ts(h); if (sizeof...(t)) cerr << ", ";
  154. DBG(t...); }
  155. #ifdef LOCAL // compile with -DLOCAL
  156. #define dbg(...) cerr << "LINE(" << __LINE__ << ") -> [" << #__VA_ARGS__ << "]: [", DBG(__VA_ARGS__)
  157. #else
  158. #define dbg(...) 0
  159. #endif
  160.  
  161. // FILE I/O
  162. void setIn(str s) { freopen(s.c_str(),"r",stdin); }
  163. void setOut(str s) { freopen(s.c_str(),"w",stdout); }
  164. void unsyncIO() { ios_base::sync_with_stdio(0); cin.tie(0); }
  165. void setIO(str s = "") {
  166. unsyncIO();
  167. // cin.exceptions(cin.failbit);
  168. // throws exception when do smth illegal
  169. // ex. try to read letter into int
  170. if (sz(s)) { setIn(s+".in"), setOut(s+".out"); } // for USACO
  171. }
  172.  
  173. /**
  174.  * Description: Disjoint Set Union with Rollback
  175.  * Source: see DSU
  176.  * Verification: *
  177.  */
  178.  
  179. struct DSUrb {
  180. vi e, off; void init(int n) { e = vi(n,-1); off = vi(n); }
  181. pi get(int x) {
  182. int OFF = 0;
  183. while (e[x] >= 0) {
  184. OFF ^= off[x];
  185. x = e[x];
  186. }
  187. return {x,OFF};
  188. }
  189. vector<array<int,4>> mod;
  190. int unite(int _x, int _y) { // union by size
  191. pi x = get(_x), y = get(_y);
  192. if (x.f == y.f) {
  193. if (x.s == y.s) return 0;
  194. mod.pb({-1,-1,-1,-1});
  195. return 1;
  196. }
  197. if (e[x.f] > e[y.f]) swap(x,y);
  198. mod.pb({x.f,y.f,e[x.f],e[y.f]});
  199. e[x.f] += e[y.f]; e[y.f] = x.f; off[y.f] = x.s^y.s^1;
  200. return 1;
  201. }
  202. void rollback() {
  203. auto a = mod.bk; mod.pop_back();
  204. if (a[0] != -1) e[a[0]] = a[2], e[a[1]] = a[3];
  205. }
  206. };
  207.  
  208. DSUrb D;
  209. int N,M,Q;
  210. int fst[MX],u[MX],v[MX];
  211.  
  212. bool ad(int ind) {
  213. dbg("AD",ind);
  214. if (ind == M+1) return 1;
  215. return D.unite(u[ind],v[ind]);
  216. }
  217. void restore(int _sz) {
  218. while (sz(D.mod) > _sz) {
  219. D.rollback();
  220. dbg("ROLLBACK");
  221. }
  222. }
  223.  
  224. void divi(int xl, int xr, int yl, int yr) {
  225. // removing xr ... yr is bipartite, move ? left while possible
  226. if (xl > xr) return;
  227. dbg("DIVI",xl,xr,yl,yr,sz(D.mod));
  228. assert(yl <= yr);
  229. int xm = (xl+xr)/2;
  230. int res = -1;
  231. int _sz = sz(D.mod);
  232. FOR(i,xl,xm) if (!ad(i)) {
  233. res = yr; assert(res == M+1);
  234. break;
  235. }
  236. int _sz2 = sz(D.mod);
  237. if (res == -1) {
  238. int i = yr; while (i > yl && ad(i)) i --;
  239. res = i;
  240. }
  241. fst[xm] = res;
  242. dbg("SET",xm,fst[xm]);
  243. if (fst[xm] == M+1) {
  244. FOR(i,xm+1,xr+1) fst[i] = M+1;
  245. } else {
  246. restore(_sz2);
  247. if (!ad(xm)) {
  248. FOR(i,xm+1,xr+1) fst[i] = M+1;
  249. } else {
  250. divi(xm+1,xr,fst[xm],yr);
  251. }
  252. }
  253. restore(_sz);
  254. FOR(i,fst[xm]+1,yr+1) assert(ad(i));
  255. divi(xl,xm-1,yl,fst[xm]); // add those from fst[xm] to r-1
  256. restore(_sz);
  257. }
  258.  
  259. int main() {
  260. setIO(); re(N,M,Q); D.init(N+1);
  261. FOR(i,1,M+1) re(u[i],v[i]);
  262. divi(1,M,1,M+1);
  263. FOR(i,1,M+1) dbg(i,fst[i]);
  264. // FOR(i,1,M+1) { // M^2 * DSU solution
  265. // DSUrb D; D.init(N+1);
  266. // FOR(j,1,i) {
  267. // if (!D.unite(u[j],v[j])) {
  268. // fst[i] = M+1;
  269. // break;
  270. // }
  271. // dbg("UNITED",u[j],v[j]);
  272. // }
  273. // if (fst[i] == M+1) continue;
  274. // int j = M;
  275. // while (j >= i) {
  276. // if (D.unite(u[j],v[j])) j --;
  277. // else {
  278. // dbg("NOPE",u[j],v[j]);
  279. // break;
  280. // }
  281. // }
  282. // fst[i] = j;
  283. // dbg(i,fst[i]);
  284. // }
  285. F0R(i,Q) {
  286. int l,r; re(l,r);
  287. if (r >= fst[l]) ps("NO");
  288. else ps("YES");
  289. }
  290. // you should actually read the stuff at the bottom
  291. }
  292.  
  293. /* stuff you should look for
  294. * int overflow, array bounds
  295. * special cases (n=1?)
  296. * do smth instead of nothing and stay organized
  297. * WRITE STUFF DOWN
  298. */
  299.  
  300.  
Success #stdin #stdout 0s 4312KB
stdin
Standard input is empty
stdout
Standard output is empty