Problem:
Score : 600 points

Problem Statement

Given are an integer N and arrays S, T, U, and V, each of length N.
Construct an N×N matrix a that satisfy the following conditions:

a_{i,j} is an integer.

0 \leq a_{i,j} \lt 2^{64}.

If S_{i} = 0, the bitwise AND of the elements in the i-th row is U_{i}.

If S_{i} = 1, the bitwise OR of the elements in the i-th row is U_{i}.

If T_{i} = 0, the bitwise AND of the elements in the i-th column is V_{i}.

If T_{i} = 1, the bitwise OR of the elements in the i-th column is V_{i}.

However, there may be cases where no matrix satisfies the conditions.

Constraints

All values in input are integers.

1 \leq N \leq 500

0 \leq S_{i} \leq 1

0 \leq T_{i} \leq 1

0 \leq U_{i} \lt 2^{64}

0 \leq V_{i} \lt 2^{64}

Input

Input is given from Standard Input in the following format:

N
S_{1} S_{2} ... S_{N}
T_{1} T_{2} ... T_{N}
U_{1} U_{2} ... U_{N}
V_{1} V_{2} ... V_{N}

Output

If there exists a matrix that satisfies the conditions, print one such matrix in the following format:

a_{1,1} ... a_{1,N}
:
a_{N,1} ... a_{N,N}

Note that any matrix satisfying the conditions is accepted.

If no matrix satisfies the conditions, print -1.

Sample Input 1

2
0 1
1 0
1 1
1 0

Sample Output 1

1 1
1 0

In Sample Input 1, we need to find a matrix such that:

the bitwise AND of the elements in the 1-st row is 1;

the bitwise OR of the elements in the 2-nd row is 1;

the bitwise OR of the elements in the 1-st column is 1;

the bitwise AND of the elements in the 2-nd column is 0.

Sample Input 2

2
1 1
1 0
15 15
15 11

Sample Output 2

15 11
15 11

Solution in Python (3.8.2) (judge verdict: Time Limit Exceeded)

# simple-sat program by sahands
# https://github.com/sahands/simple-sat
# Licensed under MIT License


from collections import deque
import sys


class SATInstance(object):
    def parse_and_add_clause(self, line):
        clause = []
        for literal in line.split():
            negated = 1 if literal.startswith('~') else 0
            variable = literal[negated:]
            if variable not in self.variable_table:
                self.variable_table[variable] = len(self.variables)
                self.variables.append(variable)
            encoded_literal = self.variable_table[variable] << 1 | negated
            clause.append(encoded_literal)
        self.clauses.append(tuple(set(clause)))

    def __init__(self):
        self.variables = []
        self.variable_table = dict()
        self.clauses = []

    @classmethod
    def from_file(cls, file):
        instance = cls()
        for line in file:
            line = line.strip()
            if len(line) > 0 and not line.startswith('#'):
                instance.parse_and_add_clause(line)
        return instance

    @classmethod
    def from_stuv(cls, ss, ts, us, vs):
        instance = cls()
        n = len(ss)
        for i in range(n * n):
            instance.variable_table[i] = i
            instance.variables.append(i)
        for i, (s, u) in enumerate(zip(ss, us)):
            if s == 0 and u == 0:
                clause = []
                for j in range(n):
                    negated = 1
                    encoded_literal = (i * n + j) << 1 | negated
                    clause.append(encoded_literal)
                instance.clauses.append(tuple(set(clause)))
            if s == 0 and u == 1:
                for j in range(n):
                    clause = []
                    negated = 0
                    encoded_literal = (i * n + j) << 1 | negated
                    clause.append(encoded_literal)
                    instance.clauses.append(tuple(set(clause)))
            if s == 1 and u == 1:
                clause = []
                for j in range(n):
                    negated = 0
                    encoded_literal = (i * n + j) << 1 | negated
                    clause.append(encoded_literal)
                instance.clauses.append(tuple(set(clause)))
            if s == 1 and u == 0:
                for j in range(n):
                    clause = []
                    negated = 1
                    encoded_literal = (i * n + j) << 1 | negated
                    clause.append(encoded_literal)
                    instance.clauses.append(tuple(set(clause)))
        for i, (t, v) in enumerate(zip(ts, vs)):
            if t == 0 and v == 0:
                clause = []
                for j in range(n):
                    negated = 1
                    encoded_literal = (j * n + i) << 1 | negated
                    clause.append(encoded_literal)
                instance.clauses.append(tuple(set(clause)))
            if t == 0 and v == 1:
                for j in range(n):
                    clause = []
                    negated = 0
                    encoded_literal = (j * n + i) << 1 | negated
                    clause.append(encoded_literal)
                    instance.clauses.append(tuple(set(clause)))
            if t == 1 and v == 1:
                clause = []
                for j in range(n):
                    negated = 0
                    encoded_literal = (j * n + i) << 1 | negated
                    clause.append(encoded_literal)
                instance.clauses.append(tuple(set(clause)))
            if t == 1 and v == 0:
                for j in range(n):
                    clause = []
                    negated = 1
                    encoded_literal = (j * n + i) << 1 | negated
                    clause.append(encoded_literal)
                    instance.clauses.append(tuple(set(clause)))

        return instance

    def literal_to_string(self, literal):
        s = '~' if literal & 1 else ''
        return s + self.variables[literal >> 1]

    def clause_to_string(self, clause):
        return ' '.join(self.literal_to_string(l) for l in clause)

    def assignment_to_string(self, assignment, brief=False, starting_with=''):
        literals = []
        for a, v in ((a, v) for a, v in zip(assignment, self.variables)
                     if v.startswith(starting_with)):
            if a == 0 and not brief:
                literals.append('~' + v)
            elif a:
                literals.append(v)
        return ' '.join(literals)


def setup_watchlist(instance):
    watchlist = [deque() for __ in range(2 * len(instance.variables))]
    for clause in instance.clauses:
        # Make the clause watch its first literal
        watchlist[clause[0]].append(clause)
    return watchlist


def update_watchlist(watchlist,
                     false_literal,
                     assignment):
    """
    Updates the watch list after literal 'false_literal' was just assigned
    False, by making any clause watching false_literal watch something else.
    Returns False it is impossible to do so, meaning a clause is contradicted
    by the current assignment.
    """
    while watchlist[false_literal]:
        clause = watchlist[false_literal][0]
        found_alternative = False
        for alternative in clause:
            v = alternative >> 1
            a = alternative & 1
            if assignment[v] is None or assignment[v] == a ^ 1:
                found_alternative = True
                del watchlist[false_literal][0]
                watchlist[alternative].append(clause)
                break

        if not found_alternative:
            return False
    return True


def solve(instance, watchlist, assignment, d):
    """
    Iteratively solve SAT by assigning to variables d, d+1, ..., n-1. Assumes
    variables 0, ..., d-1 are assigned so far. A generator for all the
    satisfying assignments is returned.
    """

    # The state list wil keep track of what values for which variables
    # we have tried so far. A value of 0 means nothing has been tried yet,
    # a value of 1 means False has been tried but not True, 2 means True but
    # not False, and 3 means both have been tried.
    n = len(instance.variables)
    state = [0] * n

    while True:
        if d == n:
            yield assignment
            d -= 1
            continue
        # Let's try assigning a value to v. Here would be the place to insert
        # heuristics of which value to try first.
        tried_something = False
        for a in [0, 1]:
            if (state[d] >> a) & 1 == 0:
                tried_something = True
                # Set the bit indicating a has been tried for d
                state[d] |= 1 << a
                assignment[d] = a
                if not update_watchlist(watchlist,
                                        d << 1 | a,
                                        assignment):
                    assignment[d] = None
                else:
                    d += 1
                    break

        if not tried_something:
            if d == 0:
                # Can't backtrack further. No solutions.
                return
            else:
                # Backtrack
                state[d] = 0
                assignment[d] = None
                d -= 1


n = int(input())
ss = list(map(int, input().split()))
ts = list(map(int, input().split()))
us = list(map(int, input().split()))
vs = list(map(int, input().split()))


ans = [0] * (n * n)
for bit in range(64):
    instance = SATInstance.from_stuv(
        ss, ts,
        [(s >> bit) & 1 for s in us],
        [(s >> bit) & 1 for s in vs])
    n2 = len(instance.variables)
    watchlist = setup_watchlist(instance)
    assignment = [None] * n2
    solution = solve(instance, watchlist, assignment, 0)
    solutions = []
    for v in solution:
        solutions.append(v)
        break
    if len(solutions) == 0:
        print(-1)
        sys.exit()
    for i, v in enumerate(solutions[0]):
        ans[i] |= v << bit

for x in range(n):
    print(' '.join(map(str, ans[(x * n):((x + 1) * n)])))