#pragma once
#include"src/flows/dinic.hpp"/**
* Author: Teetat T.
* Date: 2024-07-16
* Description: Binary Optimization.
* minimize $\kappa + \sum_i \theta_i(x_i) + \sum_{i<j} \phi_{ij}(x_i,x_j) + \sum_{i<j<k} \psi_{ijk}(x_i,x_j,x_k)$
* where $x_i \in \{0,1\}$ and $\phi_{ij},\psi_{ijk}$ are submodular functions.
* a set function $f$ is submodular if $f(S) + f(T) \geq f(S \cap T) + f(S \cup T)$ for all $S,T$.
* $\phi_{ij}(0,1) + \phi_{ij}(1,0) \geq \phi_{ij}(1,1) + \phi_{ij}(0,0)$.
*/template<classT,boolminimize=true>structBinaryOptimization{staticconstexprTINF=numeric_limits<T>::max()/2;intn,s,t,buf;Tbase;map<pair<int,int>,T>edges;BinaryOptimization(int_n):n(_n),s(n),t(n+1),buf(n+2),base(0){}voidadd_edge(intu,intv,Tw){assert(w>=0);if(u==v||w==0)return;auto&e=edges[{u,v}];e=min(e+w,INF);}voidadd0(Tw){base+=w;}void_add1(inti,Ta,Tb){if(a<=b){add0(a);add_edge(s,i,b-a);}else{add0(b);add_edge(i,t,a-b);}}voidadd1(inti,Tx0,Tx1){assert(0<=i&&i<n);if(!minimize)x0=-x0,x1=-x1;_add1(i,x0,x1);}void_add2(inti,intj,Ta,Tb,Tc,Td){assert(b+c>=a+d);add0(a);_add1(i,0,c-a);_add1(j,0,d-c);add_edge(i,j,b+c-a-d);}voidadd2(inti,intj,Tx00,Tx01,Tx10,Tx11){assert(i!=j&&0<=i&&i<n&&0<=j&&j<n);if(!minimize)x00=-x00,x01=-x01,x10=-x10,x11=-x11;_add2(i,j,x00,x01,x10,x11);}void_add3(inti,intj,intk,Ta,Tb,Tc,Td,Te,Tf,Tg,Th){Tp=a+d+f+g-b-c-e-h;if(p>=0){add0(a);_add1(i,0,f-b);_add1(j,0,g-e);_add1(k,0,d-c);_add2(i,j,0,c+e-a-g,0,0);_add2(i,k,0,0,b+e-a-f,0);_add2(j,k,0,b+c-a-d,0,0);intu=buf++;add0(-p);add_edge(i,u,p);add_edge(j,u,p);add_edge(k,u,p);add_edge(u,t,p);}else{add0(h);_add1(i,c-g,0);_add1(j,b-d,0);_add1(k,e-f,0);_add2(i,j,0,0,d+f-b-h,0);_add2(i,k,0,d+g-c-h,0,0);_add2(j,k,0,0,f+g-e-h,0);intu=buf++;add0(p);add_edge(s,u,-p);add_edge(u,i,-p);add_edge(u,j,-p);add_edge(u,k,-p);}}voidadd3(inti,intj,intk,Tx000,Tx001,Tx010,Tx011,Tx100,Tx101,Tx110,Tx111){assert(i!=j&&j!=k&&k!=i&&0<=i&&i<n&&0<=j&&j<n&&0<=k&&k<n);if(!minimize){x000=-x000,x001=-x001,x010=-x010,x011=-x011;x100=-x100,x101=-x101,x110=-x110,x111=-x111;}_add3(i,j,k,x000,x001,x010,x011,x100,x101,x110,x111);}pair<T,vector<int>>solve(){Dinic<T>dinic(buf,s,t);for(auto&[p,w]:edges){auto[u,v]=p;dinic.add_edge(u,v,w);}auto[ans,cut]=dinic.cut();ans+=base;ans=min(ans,INF);cut.resize(n);return{minimize?ans:-ans,cut};}};
#line 2 "src/flows/dinic.hpp"
/**
* Author: Teetat T.
* Date: 2024-07-15
* Description: Dinic's Algorithm for finding the maximum flow.
* Time: O(V E \log U) where U is the maximum flow.
*/template<classT,booldirected=true,boolscaling=true>structDinic{staticconstexprTINF=numeric_limits<T>::max()/2;structEdge{intto;Tflow,cap;Edge(int_to,T_cap):to(_to),flow(0),cap(_cap){}Tremain(){returncap-flow;}};intn,s,t;TU;vector<Edge>e;vector<vector<int>>g;vector<int>ptr,lv;boolcalculated;Tmax_flow;Dinic(){}Dinic(intn,ints,intt){init(n,s,t);}voidinit(int_n,int_s,int_t){n=_n,s=_s,t=_t;U=0;e.clear();g.assign(n,{});calculated=false;}voidadd_edge(intfrom,intto,Tcap){assert(0<=from&&from<n&&0<=to&&to<n);g[from].emplace_back(e.size());e.emplace_back(to,cap);g[to].emplace_back(e.size());e.emplace_back(from,directed?0:cap);U=max(U,cap);}boolbfs(Tscale){lv.assign(n,-1);vector<int>q{s};lv[s]=0;for(inti=0;i<(int)q.size();i++){intu=q[i];for(intj:g[u]){intv=e[j].to;if(lv[v]==-1&&e[j].remain()>=scale){q.emplace_back(v);lv[v]=lv[u]+1;}}}returnlv[t]!=-1;}Tdfs(intu,intt,Tf){if(u==t||f==0)returnf;for(int&i=ptr[u];i<(int)g[u].size();i++){intj=g[u][i];intv=e[j].to;if(lv[v]==lv[u]+1){Tres=dfs(v,t,min(f,e[j].remain()));if(res>0){e[j].flow+=res;e[j^1].flow-=res;returnres;}}}return0;}Tflow(){if(calculated)returnmax_flow;calculated=true;max_flow=0;for(Tscale=scaling?1LL<<(63-__builtin_clzll(U)):1LL;scale>0;scale>>=1){while(bfs(scale)){ptr.assign(n,0);while(true){Tf=dfs(s,t,INF);if(f==0)break;max_flow+=f;}}}returnmax_flow;}pair<T,vector<int>>cut(){flow();vector<int>res(n);for(inti=0;i<n;i++)res[i]=(lv[i]==-1);return{max_flow,res};}};#line 3 "src/flows/binary-optimization.hpp"
/**
* Author: Teetat T.
* Date: 2024-07-16
* Description: Binary Optimization.
* minimize $\kappa + \sum_i \theta_i(x_i) + \sum_{i<j} \phi_{ij}(x_i,x_j) + \sum_{i<j<k} \psi_{ijk}(x_i,x_j,x_k)$
* where $x_i \in \{0,1\}$ and $\phi_{ij},\psi_{ijk}$ are submodular functions.
* a set function $f$ is submodular if $f(S) + f(T) \geq f(S \cap T) + f(S \cup T)$ for all $S,T$.
* $\phi_{ij}(0,1) + \phi_{ij}(1,0) \geq \phi_{ij}(1,1) + \phi_{ij}(0,0)$.
*/template<classT,boolminimize=true>structBinaryOptimization{staticconstexprTINF=numeric_limits<T>::max()/2;intn,s,t,buf;Tbase;map<pair<int,int>,T>edges;BinaryOptimization(int_n):n(_n),s(n),t(n+1),buf(n+2),base(0){}voidadd_edge(intu,intv,Tw){assert(w>=0);if(u==v||w==0)return;auto&e=edges[{u,v}];e=min(e+w,INF);}voidadd0(Tw){base+=w;}void_add1(inti,Ta,Tb){if(a<=b){add0(a);add_edge(s,i,b-a);}else{add0(b);add_edge(i,t,a-b);}}voidadd1(inti,Tx0,Tx1){assert(0<=i&&i<n);if(!minimize)x0=-x0,x1=-x1;_add1(i,x0,x1);}void_add2(inti,intj,Ta,Tb,Tc,Td){assert(b+c>=a+d);add0(a);_add1(i,0,c-a);_add1(j,0,d-c);add_edge(i,j,b+c-a-d);}voidadd2(inti,intj,Tx00,Tx01,Tx10,Tx11){assert(i!=j&&0<=i&&i<n&&0<=j&&j<n);if(!minimize)x00=-x00,x01=-x01,x10=-x10,x11=-x11;_add2(i,j,x00,x01,x10,x11);}void_add3(inti,intj,intk,Ta,Tb,Tc,Td,Te,Tf,Tg,Th){Tp=a+d+f+g-b-c-e-h;if(p>=0){add0(a);_add1(i,0,f-b);_add1(j,0,g-e);_add1(k,0,d-c);_add2(i,j,0,c+e-a-g,0,0);_add2(i,k,0,0,b+e-a-f,0);_add2(j,k,0,b+c-a-d,0,0);intu=buf++;add0(-p);add_edge(i,u,p);add_edge(j,u,p);add_edge(k,u,p);add_edge(u,t,p);}else{add0(h);_add1(i,c-g,0);_add1(j,b-d,0);_add1(k,e-f,0);_add2(i,j,0,0,d+f-b-h,0);_add2(i,k,0,d+g-c-h,0,0);_add2(j,k,0,0,f+g-e-h,0);intu=buf++;add0(p);add_edge(s,u,-p);add_edge(u,i,-p);add_edge(u,j,-p);add_edge(u,k,-p);}}voidadd3(inti,intj,intk,Tx000,Tx001,Tx010,Tx011,Tx100,Tx101,Tx110,Tx111){assert(i!=j&&j!=k&&k!=i&&0<=i&&i<n&&0<=j&&j<n&&0<=k&&k<n);if(!minimize){x000=-x000,x001=-x001,x010=-x010,x011=-x011;x100=-x100,x101=-x101,x110=-x110,x111=-x111;}_add3(i,j,k,x000,x001,x010,x011,x100,x101,x110,x111);}pair<T,vector<int>>solve(){Dinic<T>dinic(buf,s,t);for(auto&[p,w]:edges){auto[u,v]=p;dinic.add_edge(u,v,w);}auto[ans,cut]=dinic.cut();ans+=base;ans=min(ans,INF);cut.resize(n);return{minimize?ans:-ans,cut};}};