#pragma GCC target("avx2") #pragma GCC optimize("O3") #pragma GCC optimize("unroll-loops") #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include using namespace std; using namespace atcoder; //using mint = modint998244353; #define rep(i,n) for (int i=0;i-1;i--) #define append push_back #define all(x) (x).begin(), (x).end() template using vec = vector; template using vvec = vec>; template using vvvec = vec>; using ll = long long; using pii = pair; using pll = pair; template bool chmin(T &a, T b){ if (a>b){ a = b; return true; } return false; } template bool chmax(T &a, T b){ if (a T sum(vec x){ T res=0; for (auto e:x){ res += e; } return res; } template void printv(vec x){ for (auto e:x){ cout<>= 1; } return res; } int op1(int i,int j){ return min(i,j); } int e1(){ return 1e5; } int op2(int i,int j){ return max(i,j); } int e2(){ return -1; } int A[100000]; int B[100000]; bool direct(int i,int j){ if (i < j){ return (A[i] < B[j]); } else{ return (B[i] < A[j]); } } vec hamilton_path(vec V){ int n = V.size(); if (n <= 1){ return V; } vec VA = hamilton_path({V.begin(),V.begin()+(n/2)}); vec VB = hamilton_path({V.begin()+(n/2),V.begin()+(n)}); vec res = {}; int i = 0; for (auto a:VA){ while (i < VB.size() && direct(VB[i],a)){ res.append(VB[i]); i++; } res.append(a); } for (int j=i;j solve(){ int N,M; cin>>N>>M; for (int i=0;i>A[i]; A[i]--; } for (int i=0;i>B[i]; B[i]--; } vec> edge(N,vec(0)); int u,v; for (int i=0;i>u>>v; edge[u-1].append(v-1); edge[v-1].append(u-1); } vec new_E = {}; vec group(N,0); for (int i=0;i mex(n+1,false); for (auto nv:edge[i]){ if (nv < i && group[nv]<=n){ mex[group[nv]] = true; } } for (int j=0;j> clique(n,vec(0)); rep(v,N){ clique[group[v]].append(v); } vec idx(N,-1); for (int i=0;i memo_to(N,1e5); vec memo_from(N,-1); vec ci(n); rep(i,n){ci[i]=i;}; sort(all(ci),[&clique](int i,int j){ return clique[i].size() < clique[j].size(); }); vec idx_on_ci(n); rep(i,n){idx_on_ci[ci[i]]=i;}; vec> ban(N,vec(0)); vec Vs = {}; segtree seg_to_large(2*N); segtree seg_to_small(2*N); segtree seg_from_large(2*N); segtree seg_from_small(2*N); rep(i,n){ int target = ci[i]; for (auto v:clique[target]){ Vs.append(v); } sort(all(Vs)); for (auto nv:clique[target]){ for (auto v:edge[nv]){ if (idx_on_ci[group[v]] <= i){ ban[v].append(nv); } } } rrep(j,Vs.size()){ v = Vs[j]; for (auto nv:ban[v]){ if (v < nv){ seg_to_large.set(B[nv],1e5); } } chmin(memo_to[v],seg_to_large.prod(A[v],2*N)); for (auto nv:ban[v]){ if (v < nv){ seg_to_large.set(B[nv],idx[nv]); } } if (group[v]==target){ seg_to_large.set(B[v],idx[v]); } } rep(j,Vs.size()){ v = Vs[j]; for (auto nv:ban[v]){ if (nv < v){ seg_to_small.set(A[nv],1e5); } } chmin(memo_to[v],seg_to_small.prod(B[v],2*N)); for (auto nv:ban[v]){ if (nv < v){ seg_to_small.set(A[nv],idx[nv]); } } if (group[v]==target){ seg_to_small.set(A[v],idx[v]); } } rrep(j,Vs.size()){ v = Vs[j]; for (auto nv:ban[v]){ if (v < nv){ seg_from_large.set(B[nv],-1); } } chmax(memo_from[v],seg_from_large.prod(0,A[v])); for (auto nv:ban[v]){ if (v < nv){ seg_from_large.set(B[nv],idx[nv]); } } if (group[v]==target){ seg_from_large.set(B[v],idx[v]); } } rep(j,Vs.size()){ v = Vs[j]; for (auto nv:ban[v]){ if (nv < v){ seg_from_small.set(A[nv],-1); } } chmax(memo_from[v],seg_from_small.prod(0,B[v])); for (auto nv:ban[v]){ if (nv < v){ seg_from_small.set(A[nv],idx[nv]); } } if (group[v]==target){ seg_from_small.set(A[v],idx[v]); } } for (auto v:Vs){ if (memo_to[v]!=1e5){ int nv = clique[target][memo_to[v]]; new_E.append({v,nv}); memo_to[v] = 1e5; } if (memo_from[v]!=-1){ int pv = clique[target][memo_from[v]]; new_E.append({pv,v}); memo_from[v] = -1; } ban[v] = {}; if (group[v]==target){ seg_to_large.set(B[v],1e5); seg_to_small.set(A[v],1e5); seg_from_large.set(B[v],-1); seg_from_small.set(A[v],-1) ; } } } sort(all(new_E)); new_E.erase(unique(all(new_E)),new_E.end()); return new_E; } int main(){ ios::sync_with_stdio(false); std::cin.tie(nullptr); auto res = solve(); cout<