Problem:
Score : 700 points

Problem Statement

Aoki is playing with a sequence of numbers a_{1}, a_{2}, ..., a_{N}. Every second, he performs the following operation :

Choose a positive integer k. For each element of the sequence v, Aoki may choose to replace v with its remainder when divided by k, or do nothing with v. The cost of this operation is 2^{k} (regardless of how many elements he changes).

Aoki wants to turn the sequence into b_{1}, b_{2}, ..., b_{N} (the order of the elements is important). Determine if it is possible for Aoki to perform this task and if yes, find the minimum cost required.

Constraints

1 \leq N \leq 50

0 \leq a_{i}, b_{i} \leq 50

All values in the input are integers.

Input

Input is given from Standard Input in the following format:

N
a_{1} a_{2} ... a_{N}
b_{1} b_{2} ... b_{N}

Output

Print the minimum cost required to turn the original sequence into b_{1}, b_{2}, ..., b_{N}. If the task is impossible, output -1 instead.

Sample Input 1

3
19 10 14
0 3 4

Sample Output 1

160

Here's a possible sequence of operations :

Choose k = 7. Replace 19 with 5, 10 with 3 and do nothing to 14. The sequence is now 5, 3, 14.

Choose k = 5. Replace 5 with 0, do nothing to 3 and replace 14 with 4. The sequence is now 0, 3, 4.

The total cost is 2^{7} + 2^{5} = 160.

Sample Input 2

3
19 15 14
0 0 0

Sample Output 2

2

Aoki can just choose k = 1 and turn everything into 0. The cost is 2^{1} = 2.

Sample Input 3

2
8 13
5 13

Sample Output 3

-1

The task is impossible because we can never turn 8 into 5 using the given operation.

Sample Input 4

4
2 0 1 8
2 0 1 8

Sample Output 4

0

Aoki doesn't need to do anything here. The cost is 0.

Sample Input 5

1
50
13

Sample Output 5

137438953472

Beware of overflow issues.

Solution in C++14 (GCC 5.4.1) (judge verdict: Wrong Answer)

// 基本テンプレート
 
#include <iostream>
#include <iomanip>
#include <cstdio>
#include <string>
#include <cstring>
#include <deque>
#include <list>
#include <queue>
#include <stack>
#include <vector>
#include <utility>
#include <algorithm>
#include <map>
#include <set>
#include <complex>
#include <cmath>
#include <limits>
#include <cfloat>
#include <climits>
#include <ctime>
#include <cassert>
#include <numeric>
#include <fstream>
#include <functional>
using namespace std;
 
#define rep(i,a,n) for(int (i)=(a); (i)<(n); (i)++)
#define repq(i,a,n) for(int (i)=(a); (i)<=(n); (i)++)
#define repr(i,a,n) for(int (i)=(a); (i)>=(n); (i)--)
#define debug(...) fprintf(stderr, __VA_ARGS__)
#define int long long int
 
template<typename T> void chmax(T &a, T b) {a = max(a, b);}
template<typename T> void chmin(T &a, T b) {a = min(a, b);}
template<typename T> void chadd(T &a, T b) {a = a + b;}
 
typedef pair<int, int> pii;
typedef long long ll;
 
int dx[] = {0, 0, 1, -1};
int dy[] = {1, -1, 0, 0};
const ll INF = 1LL << 60;
const ll MOD = 1000000007LL;

const int B = 60;
int N, a[B], b[B];

int func(vector<pii> &ope) {
    int ans = 0;
    rep(z,0,N) {
        int i = ope[z].second;
        int s = a[i], t = b[i];
        if(s < t) {
            return INF;
        }

        vector<int> dist(B, INF), mon(B);
        dist[s] = 0;
        rep(k,0,B) {
            if(!(ans >> k & 1)) mon[k] = (1LL << k);
        }

        priority_queue< pii, vector<pii>, greater<pii> > que;
        que.push(make_pair(dist[s], s));

        while(que.size()) {
            pii cur = que.top(); que.pop();
            int cost = cur.first, mo = cur.second;
            for(int k=1; k<=mo; k++) {
                int n_mo = mo % k;
                int n_cost = cost + mon[k];
                if(dist[n_mo] > n_cost) {
                    dist[n_mo] = n_cost;
                    que.push(make_pair(dist[n_mo], n_mo));
                }
            }
        }
        ans |= dist[t];
    }
    return ans;
}

signed main() {
    cin >> N;
    
    bool ok = true;
    rep(i,0,N) cin >> a[i];
    rep(i,0,N) cin >> b[i];

    vector<pii> ope;
    rep(i,0,N) {
        int s = a[i], t = b[i];
        // printf("s = %lld, t = %lld\n", s, t);
        if(s < t) {
            ok = false;
            continue;
        }

        vector<int> dist(B, INF);
        dist[s] = 0;

        priority_queue< pii, vector<pii>, greater<pii> > que;
        que.push(make_pair(dist[s], s));

        while(que.size()) {
            pii cur = que.top(); que.pop();
            int cost = cur.first, mo = cur.second;
            for(int k=1; k<=mo; k++) {
                int n_mo = mo % k;
                int n_cost = cost + (1LL << k);
                if(dist[n_mo] > n_cost) {
                    dist[n_mo] = n_cost;
                    que.push(make_pair(dist[n_mo], n_mo));
                }
            }
        }
        ope.push_back(make_pair(dist[t], i));
    }

    int ans = INF;
    rep(i,0,3000) {
        random_shuffle(ope.begin(), ope.end());
        chmin(ans, func(ope));
    }

    if(ans == INF) ok = false;
    cout << (ok ? ans : -1) << endl;
    return 0;
}