Language: C++

#include<iostream>
#include<algorithm>
#include<vector>
#include<tuple>
#include<queue>
#include<functional>

using namespace std;

typedef long long ll;
typedef tuple < ll, int, bool > T3;//値, もともとの位置, 表裏(trueなら裏)

template <class Monoid> struct SegTree {
	int N;
	vector<Monoid> node;
	std::function<Monoid(Monoid, Monoid)> operation;
	Monoid unit;//単位元

	std::function<bool(Monoid, Monoid)> comp;
	Monoid not_find_sgn;

	SegTree(vector<Monoid>& data, std::function<Monoid(Monoid, Monoid)> op, Monoid U) {
		//データ　演算　単位元
		operation = op;
		unit = U;
		int size = data.size();
		N = 1;
		while (N < size)N <<= 1;
		node.resize(2 * N - 1, unit);

		for (int i = 0; i < size; i++) {
			node[i + N - 1] = data[i];
		}

		for (int i = N - 2; i >= 0; i--) {
			node[i] = operation(node[i * 2 + 1], node[i * 2 + 2]);
		}
	}

	void update(int pos, Monoid val) {
		pos += N - 1;
		node[pos] = val;
		while (pos > 0) {
			pos = (pos - 1) / 2;
			node[pos] = operation(node[pos * 2 + 1], node[pos * 2 + 2]);
		}
	}

	Monoid getval(int a, int b, int idx, int l, int r = -1) {
		//[a, b)を求める。　使い方はgetval(a, b, );
		if (r == -1)r = N;
		if (b <= l || r <= a)return unit;
		if (a <= l && r <= b)return node[idx];
		Monoid left = getval(a, b, idx * 2 + 1, l, (l + r) / 2);
		Monoid right = getval(a, b, idx * 2 + 2, (l + r) / 2, r);
		return operation(left, right);
	}

	Monoid getval(int a, int b) {
		//ラッパー。
		return getval(a, b, 0, 0, -1);
	}

	//必ずセットしてから二分探索すること
	void setcomp(std::function<bool(Monoid, Monoid)> _comp, Monoid _nfs) {
		comp = _comp;
		not_find_sgn = _nfs;
	}

	//大丈夫か？
	Monoid lower_bound(Monoid x, int a, int b, int l, int r, int k) {
		if (b <= l || r <= a)return not_find_sgn;
		if (!comp(x, node[k]))return not_find_sgn;
		if (k >= N - 1)return k - (N - 1);
		Monoid tmp = lower_bound(x, a, b, (l + r) / 2, r, k * 2 + 2);
		if (!comp(x, tmp))return tmp;
		return lower_bound(x, a, b, l, (l + r) / 2, k * 2 + 1);
	}
	Monoid lower_bound(Monoid x, int a, int b) {
		return lower_bound(x, a, b, 0, N, 0);
	}
	Monoid lower_bound(Monoid x) {
		return lower_bound(a, 0, N);
	}

	//たぶん大丈夫やろ
	Monoid upper_bound(Monoid x, int a, int b, int l, int r, int k) {
		if (b <= l || r <= a)return not_find_sgn;
		if (!comp(x, node[k]))return not_find_sgn;
		if (k > N - 1)return k - (N - 1);
		Monoid tmp = lower_bound(x, a, b, (l + r) / 2, r, k * 2 + 2);
		if (!comp(x, tmp))return tmp;
		return lower_bound(x, a, b, l, (l + r) / 2, k * 2 + 1);
	}
	Monoid upper_bound(Monoid x, int a, int b) {
		return upper_bound(x, a, b, 0, N, 0);
	}
	Monoid upper_bound(Monoid x) {
		return upper_bound(a, 0, N);
	}
};

int N;
int A[50], B[50];

int tentousu(vector<int>& tmp) {
	SegTree<int> st(vector<int>(50 + 1, 0), [](int a, int b) {return a + b; }, 0);
	int ret = 0;
	for (int i = 0; i < tmp.size(); i++) {
		ret += st.getval(tmp[i] + 1, 51);
		st.update(tmp[i], 1);
	}
	return ret;
}

int main() {
	cin >> N;
	for (int i = 0; i < N; i++)cin >> A[i];
	for (int i = 0; i < N; i++)cin >> B[i];

	vector<vector<T3>> candidate;
	for (int bit = 0; bit < (1 << N); bit++) {
		vector<T3> tmp;
		int cnt = 0;
		for (int i = 0; i < N; i++) {
			if ((bit >> i) & 1) {
				//裏返す
				cnt++;
				tmp.push_back(make_tuple(B[i], i, true));
			}
			else {
				tmp.push_back(make_tuple(A[i], i, false));
			}
		}
		if (cnt % 2 != 0)continue;
		sort(tmp.begin(), tmp.end());
		for (int i = 0; i < N; i++) {
			if (get<2>(tmp[i]) && abs(get<1>(tmp[i]) - i) % 2 == 1) {
				//ok
			}
			else if (!get<2>(tmp[i]) && abs(get<1>(tmp[i]) - i) % 2 == 0) {
				//ok
			}
			else {
				cnt = -1;//条件を満たさない。
			}
		}
		if (cnt == -1)continue;
		candidate.push_back(tmp);
	}

	int ans = 1145141919;
	for (int i = 0; i < candidate.size(); i++) {

		vector<queue<int>> conv(50 + 2);
		vector<bool> fl(50, 0);//i(0-idx)番目のカードが裏ならtrue、そうでなければfalse
		for (int j = 0; j < N; j++) {
			conv[get<0>(candidate[i][j])].push(j);
			fl[get<1>(candidate[i][j])] = get<2>(candidate[i][j]);
		}
		vector<int> tmp(N);//これの転倒数を求める
		for (int j = 0; j < N; j++) {
			tmp[j] = conv[(fl[j] ? B[j] : A[j])].front();
			conv[(fl[j] ? B[j] : A[j])].pop();
		}

		ans = min(ans, tentousu(tmp));
	}

	if (ans == 1145141919)cout << -1 << endl;
	else cout << ans << endl;

	return 0;
}

Compiler output:
a.cc: In member function 'Monoid SegTree<Monoid>::lower_bound(Monoid)':
a.cc:83:36: error: 'a' was not declared in this scope
   83 |                 return lower_bound(a, 0, N);
      |                                    ^
a.cc: In member function 'Monoid SegTree<Monoid>::upper_bound(Monoid)':
a.cc:99:36: error: 'a' was not declared in this scope
   99 |                 return upper_bound(a, 0, N);
      |                                    ^
a.cc: In function 'int tentousu(std::vector<int>&)':
a.cc:107:25: error: cannot bind non-const lvalue reference of type 'std::vector<int>&' to an rvalue of type 'std::vector<int>'
  107 |         SegTree<int> st(vector<int>(50 + 1, 0), [](int a, int b) {return a + b; }, 0);
      |                         ^~~~~~~~~~~~~~~~~~~~~~
a.cc:22:33: note:   initializing argument 1 of 'SegTree<Monoid>::SegTree(std::vector<_Tp>&, std::function<Monoid(Monoid, Monoid)>, Monoid) [with Monoid = int]'
   22 |         SegTree(vector<Monoid>& data, std::function<Monoid(Monoid, Monoid)> op, Monoid U) {
      |                 ~~~~~~~~~~~~~~~~^~~~