#include<bits/stdc++.h>
using namespace std;

vector<int> add(vector<int> a,vector<int> b){
  vector<int> res(a.size());
  for(int i=0;i<(int)a.size();i++)
    res[i]=a[i]+b[i];
  return res;
}

vector<int> sub(vector<int> a){
  vector<int> res(a.size());
  for(int i=0;i<(int)a.size();i++)
    res[i]=-a[i];
  return res;
}


int change(char ch){
  int res;
  if('A'<=ch&&ch<='Z'){
    res= ch-'A';
  }else{
    res= 26+ch-'a';
  }
  return res;
}

int N;
char mp[55][55];
int t[55][55];

struct edge{
  int to;
  int cap;
  vector<int> cost;
  int rev;

  edge( int a,int b, vector<int> c,int d){
    to=a;
    cap=b;
    cost=c;
    rev=d;
  }
};

#define MAX_V 205

vector<edge> G[MAX_V];
vector<int> h[MAX_V];
vector<int> dist[MAX_V];
int prevv[MAX_V],preve[MAX_V];

void add_edge(int from,int to,int cap,vector<int> cost){
  G[from].push_back( edge(to,cap,cost,G[to].size() ) );
  G[to].push_back(   edge(from,0, sub(cost) ,G[from].size()-1 ) );
}

typedef pair< vector<int> , int > P;

vector<int> min_cost_flow(int s,int t,int f){
  vector<int> res(60,0);
  
  fill( h, h+MAX_V, vector<int>(60,0) );
  while(f>0){
    priority_queue< P , vector<P> , greater<P> > Q;
    fill(dist,dist+MAX_V, vector<int>(60,9999) );
    dist[s]= vector<int>(60,0);
    Q.push(P( dist[s] ,s));
    while(!Q.empty()){
      P p=Q.top();Q.pop();
      int v=p.second;
      if(dist[v]<p.first)continue;
      
      for(int i=0;i<(int)G[v].size();i++){
        edge &e=G[v][i];
        if(e.cap>0){

          vector<int> tmp = add(dist[v],e.cost);
          tmp=add(tmp,h[v]);
          vector<int> tmp2 = sub(h[e.to]);
          tmp = add(tmp, tmp2);

          
          if(dist[e.to]>tmp){
            dist[e.to]=tmp;
            prevv[e.to]=v;
            preve[e.to]=i;
            Q.push(P(dist[e.to],e.to));
          }
        }
      }
    }

    
    for(int v=0;v<MAX_V;v++)h[v]=add(h[v],dist[v]);
    
    f--;
    res=add(res,h[t]);
    
    for(int v=t;v!=s;v=prevv[v]){
      edge &e=G[prevv[v]][preve[v]];
      e.cap--;
      G[v][e.rev].cap++;
    }
  }
  return res;
}

int main(){
  
  cin>>N;
  int si=N+N;
  int ti=N+N+1;

  map< int , char > dm;
  for(int i=0;i<N;i++){
    for(int j=0;j<N;j++){
      char ch;
      cin>>ch;
      dm[ change(ch) ] = ch;
      mp[i][j]=ch;
    }
  }

    
  for(int i=0;i<N;i++){
    for(int j=0;j<N;j++){
      t[i][j]=G[i].size();
      vector<int> tmp(60,1000);
      tmp[ change(mp[i][j]) ]--;
      add_edge(i,N+j,1,tmp);
    }
  }

  for(int i=0;i<N;i++){
    vector<int> tmp(60,0);
    add_edge(si,i,1,tmp);
    add_edge(N+i,ti,1,tmp);
  }

  vector<int> vec = min_cost_flow(si,ti,N);

  string ans="";


  
  for(int i=0;i<60;i++){
    vec[i]=1000*N-vec[i];
    for(int j=0;j<vec[i];j++){
      ans+= dm[i];
    }
  }
  assert((int)ans.size()==N);
  sort(ans.begin(),ans.end());
  cout<<ans<<endl;
  /*
  for(int i=0;i<N;i++){
    for(int j=0;j<N;j++){
      edge e=G[i][ t[i][j] ];
      if(e.cap==0)ans+=mp[i][j];
    }
  }

  sort(ans.begin(),ans.end());
  cout<<ans<<endl;
  */
  return 0;
}
### Prompt

Construct a cpp code solution to the problem outlined:

Example

Input

3
aab
czc
baa


Output

aac

### Response

```cpp
#include<bits/stdc++.h>
using namespace std;

vector<int> add(vector<int> a,vector<int> b){
  vector<int> res(a.size());
  for(int i=0;i<(int)a.size();i++)
    res[i]=a[i]+b[i];
  return res;
}

vector<int> sub(vector<int> a){
  vector<int> res(a.size());
  for(int i=0;i<(int)a.size();i++)
    res[i]=-a[i];
  return res;
}


int change(char ch){
  int res;
  if('A'<=ch&&ch<='Z'){
    res= ch-'A';
  }else{
    res= 26+ch-'a';
  }
  return res;
}

int N;
char mp[55][55];
int t[55][55];

struct edge{
  int to;
  int cap;
  vector<int> cost;
  int rev;

  edge( int a,int b, vector<int> c,int d){
    to=a;
    cap=b;
    cost=c;
    rev=d;
  }
};

#define MAX_V 205

vector<edge> G[MAX_V];
vector<int> h[MAX_V];
vector<int> dist[MAX_V];
int prevv[MAX_V],preve[MAX_V];

void add_edge(int from,int to,int cap,vector<int> cost){
  G[from].push_back( edge(to,cap,cost,G[to].size() ) );
  G[to].push_back(   edge(from,0, sub(cost) ,G[from].size()-1 ) );
}

typedef pair< vector<int> , int > P;

vector<int> min_cost_flow(int s,int t,int f){
  vector<int> res(60,0);
  
  fill( h, h+MAX_V, vector<int>(60,0) );
  while(f>0){
    priority_queue< P , vector<P> , greater<P> > Q;
    fill(dist,dist+MAX_V, vector<int>(60,9999) );
    dist[s]= vector<int>(60,0);
    Q.push(P( dist[s] ,s));
    while(!Q.empty()){
      P p=Q.top();Q.pop();
      int v=p.second;
      if(dist[v]<p.first)continue;
      
      for(int i=0;i<(int)G[v].size();i++){
        edge &e=G[v][i];
        if(e.cap>0){

          vector<int> tmp = add(dist[v],e.cost);
          tmp=add(tmp,h[v]);
          vector<int> tmp2 = sub(h[e.to]);
          tmp = add(tmp, tmp2);

          
          if(dist[e.to]>tmp){
            dist[e.to]=tmp;
            prevv[e.to]=v;
            preve[e.to]=i;
            Q.push(P(dist[e.to],e.to));
          }
        }
      }
    }

    
    for(int v=0;v<MAX_V;v++)h[v]=add(h[v],dist[v]);
    
    f--;
    res=add(res,h[t]);
    
    for(int v=t;v!=s;v=prevv[v]){
      edge &e=G[prevv[v]][preve[v]];
      e.cap--;
      G[v][e.rev].cap++;
    }
  }
  return res;
}

int main(){
  
  cin>>N;
  int si=N+N;
  int ti=N+N+1;

  map< int , char > dm;
  for(int i=0;i<N;i++){
    for(int j=0;j<N;j++){
      char ch;
      cin>>ch;
      dm[ change(ch) ] = ch;
      mp[i][j]=ch;
    }
  }

    
  for(int i=0;i<N;i++){
    for(int j=0;j<N;j++){
      t[i][j]=G[i].size();
      vector<int> tmp(60,1000);
      tmp[ change(mp[i][j]) ]--;
      add_edge(i,N+j,1,tmp);
    }
  }

  for(int i=0;i<N;i++){
    vector<int> tmp(60,0);
    add_edge(si,i,1,tmp);
    add_edge(N+i,ti,1,tmp);
  }

  vector<int> vec = min_cost_flow(si,ti,N);

  string ans="";


  
  for(int i=0;i<60;i++){
    vec[i]=1000*N-vec[i];
    for(int j=0;j<vec[i];j++){
      ans+= dm[i];
    }
  }
  assert((int)ans.size()==N);
  sort(ans.begin(),ans.end());
  cout<<ans<<endl;
  /*
  for(int i=0;i<N;i++){
    for(int j=0;j<N;j++){
      edge e=G[i][ t[i][j] ];
      if(e.cap==0)ans+=mp[i][j];
    }
  }

  sort(ans.begin(),ans.end());
  cout<<ans<<endl;
  */
  return 0;
}
```