Language: C++

#include <climits>
#include <iostream>
#include <vector>
#include <unordered_map>
#include <tuple>

#define rep(i,i0,n) for (int (i) = (i0); (i) < (n); ++(i))

using namespace std;
using ll = long long;


int a[12][12];
int ta[12][12];
int h, h2;
int w, w2;

unordered_map< int, int*> row_keys, col_keys;

void calc_row_keys(int sel = 0, int count = 0, int last = -1) {
    if (count == w2) {
        int *arr = new int[h];
        row_keys[sel] = arr;
        rep(i, 0, h) {
            int *ai = a[i];
            vector<int> ss;
            rep(j, 0, w) {
                if (sel & (1 << j)) {
                    ss.push_back(ai[j]);
                }
            }
            sort(ss.begin(), ss.end());
            int v = 0;
            for (int ch : ss) {
                v *= 26;
                v += ch;
            }
            arr[i] = v;
        }
    } else {
        rep(j, last + 1, w) {
            calc_row_keys(sel | (1 << j), count + 1, j);
        }
    }
}

void calc_col_keys(int sel = 0, int count = 0, int last = -1) {
    if (count == h2) {
        int *arr = new int[w];
        col_keys[sel] = arr;
        rep(j, 0, w) {
            int *aj = ta[j];
            vector<int> ss;
            rep(i, 0, h) {
                if (sel & (1 << i)) {
                    ss.push_back(aj[i]);
                }
            }
            sort(ss.begin(), ss.end());
            int v = 0;
            for (int ch : ss) {
                v *= 26;
                v += ch;
            }
            arr[j] = v;
        }
    } else {
        rep(i, last + 1, h) {
            calc_col_keys(sel | (1 << i), count + 1, i);
        }
    }
}

bool check_sym1(int n, int *t) {
    int c = 0;
    rep(i, 0, n) {
        c ^= 1 << t[i];
    }
    int odd = 0;
    rep(code, 0, 26) {
        if (c & (1 << code)) {
            ++odd;
        }
    }
    return odd <= 1;
}

bool do_check_sym(int sel_rows, int sel_rows2, int center_row, int sel_cols, int sel_cols2, int center_col = -1) {

    vector< pair<ll, int> > cols, cols2, rows, rows2;

    int *keys = col_keys[sel_rows];
    int *keys2 = col_keys[sel_rows2];
    int *sc = 0;
    if (center_row != -1) {
        sc = a[center_row];
    }
    rep(j, 0, w) {
        int p2j = 1 << j;
        ll k = sc ? sc[j] : 0;
        if (p2j & sel_cols) {
            k += ((keys[j] << 12) + keys2[j]) << 5;
            cols.push_back(make_pair(k, j));
        } else if (p2j & sel_cols2) {
            k += ((keys2[j] << 12) + keys[j]) << 5;
            cols2.push_back(make_pair(k, j));
        }
    }
    sort(cols.begin(), cols.end());
    sort(cols2.begin(), cols2.end());
    rep(j, 0, w2) {
        if (cols[j].first != cols2[j].first) {
            return false;
        }
    }
    if (center_row != -1) {
        sc = a[center_row];
        rep(j, 0, w2) {
            if (sc[cols[j].second] != sc[cols2[j].second]) {
                return false;
            }
        }
    }

    keys = row_keys[sel_cols];
    keys2 = row_keys[sel_cols2];
    sc = 0;
    if (center_col != -1) {
        sc = ta[center_col];
    }
    rep(i, 0, h) {
        int p2i = 1 << i;
        ll k = sc ? sc[i] : 0;
        if (p2i & sel_rows) {
            k += ((keys[i] << 12) + keys2[i]) << 5;
            rows.push_back(make_pair(k, i));
        } else if (p2i & sel_rows2) {
            k += ((keys2[i] << 12) + keys[i]) << 5;
            rows2.push_back(make_pair(k, i));
        }
    }
    sort(rows.begin(), rows.end());
    sort(rows2.begin(), rows2.end());
    rep(i, 0, h2) {
        if (rows[i].first != rows2[i].first) {
            return false;
        }
    }
    if (center_col != -1) {
        sc = ta[center_col];
        rep(i, 0, h2) {
            if (sc[rows[i].second] != sc[rows2[i].second]) {
                return false;
            }
        }
    }

    rep(i, 0, h2) {
        int *ai = a[rows[i].second];
        int *ai2 = a[rows2[i].second];
        rep(j, 0, w2) {
            if (ai[cols[j].second] != ai2[cols2[j].second]) {
                return false;
            }
            if (ai[cols2[j].second] != ai2[cols[j].second]) {
                return false;
            }
        }
    }

    return true;
}


bool check_sym(int sel_rows, int sel_rows2, int center_row = -1) {

    int t0 = (1 << w) - 1;
    if (w % 2) {
        rep(j, 0, w) {
            int p2j = 1 << j;
            int t = t0 - p2j;
            for(auto it = row_keys.begin(); it != row_keys.end(); ++it) {
                int sel_cols = it->first;
                if (sel_cols & p2j) {
                    continue;
                }
                int sel_cols2 = t - sel_cols;
                if (sel_cols < sel_cols2) {
                    if (do_check_sym(sel_rows, sel_rows2, center_row, sel_cols, sel_cols2, j)) {
                        return true;
                    }
                }
            }
        }
        return false;
    } else {
        for(auto it = row_keys.begin(); it != row_keys.end(); ++it) {
            int sel_cols = it->first;
            int sel_cols2 = t0 - sel_cols;
            if (sel_cols < sel_cols2) {
                if (do_check_sym(sel_rows, sel_rows2, center_row, sel_cols, sel_cols2)) {
                    return true;
                }
            }
        }
        return false;
    }
}

bool solve() {

    h2 = h / 2;
    w2 = w / 2;

    if (h == 1) {
        return check_sym1(w, a[0]);
    }
    if (w == 1) {
        int b[12];
        rep(i, 0, h) {
            b[i] = a[i][0];
        }
        return check_sym1(h, b);
    }

    rep(i, 0, h) {
        int *ai = a[i];
        rep(j, 0, w) {
            ta[j][i] = ai[j];
        }
    }

    calc_row_keys();
    calc_col_keys();

    int t0 = (1 << h) - 1;
    if (h & 1) {
        rep(i, 0, h) {
            int p2i = 1 << i;
            int t = t0 - p2i;
            for(auto it = col_keys.begin(); it != col_keys.end(); ++it) {
                int sel_rows = it->first;
                if (sel_rows & p2i) {
                    continue;
                }
                int sel_rows2 = t - sel_rows;
                if (sel_rows < sel_rows2) {
                    if (check_sym(sel_rows, sel_rows2, i)) {
                        return true;
                    }
                }
            }
        }
    } else {
        for(auto it = col_keys.begin(); it != col_keys.end(); ++it) {
            int sel_rows = it->first;
            int sel_rows2 = t0 - sel_rows;
            if (sel_rows < sel_rows2) {
                if (check_sym(sel_rows, sel_rows2)) {
                    return true;
                }
            }
        }
    }

    return false;
}

int main(int argc, const char * argv[]) {
    string si;
    
    cin >> h >> w;
    rep(i, 0, h) {
        cin >> si;
        int *ai = a[i];
        rep(j, 0, w) {
            ai[j] = si[j] - 'a';
        }
    }

    cout << (solve() ? "YES" : "NO") << endl;

    return 0;
}


Compiler output:
a.cc: In function 'void calc_row_keys(int, int, int)':
a.cc:32:13: error: 'sort' was not declared in this scope; did you mean 'short'?
   32 |             sort(ss.begin(), ss.end());
      |             ^~~~
      |             short
a.cc: In function 'void calc_col_keys(int, int, int)':
a.cc:59:13: error: 'sort' was not declared in this scope; did you mean 'short'?
   59 |             sort(ss.begin(), ss.end());
      |             ^~~~
      |             short
a.cc: In function 'bool do_check_sym(int, int, int, int, int, int)':
a.cc:109:5: error: 'sort' was not declared in this scope; did you mean 'short'?
  109 |     sort(cols.begin(), cols.end());
      |     ^~~~
      |     short