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



Sample input:
2
0 1
1 0
1 1
1 0


Sample output:
1 1
1 0

Submission status: Wrong Answer

Solution code:
#!/usr/bin/env pypy3
import sys
from functools import reduce
from operator import or_, and_


def solve(N: int, S: "List[int]", T: "List[int]", U: "List[int]", V: "List[int]"):
    AND, ORE = 0, 1
    ans = [[0 for j in range(N)] for i in range(N)]
    can = True
    for b in range(1):
        parityU = [(x >> b) & 1 for x in U]
        parityV = [(x >> b) & 1 for x in V]
        can &= all(not (S[i] == ORE and parityU[i] == 0 and T[j] == AND and parityV[j] == 1) for i in range(N) for j in range(N))
        can &= all(not (S[i] == AND and parityU[i] == 1 and T[j] == ORE and parityV[j] == 0) for i in range(N) for j in range(N))
        for i in range(N):
            if S[i] == AND and parityU[i] == 1:
                for j in range(N):
                    ans[i][j] |= 1 << b
        for j in range(N):
            if T[j] == AND and parityV[j] == 1:
                for i in range(N):
                    ans[i][j] |= 1 << b
        rows_free0 = [i for i in range(N) if parityU[i] == 0 or S[i] == ORE and any(x == 1 for x in parityV)]
        rows_free1 = [i for i in range(N) if parityU[i] == 1 or S[i] == AND and any(x == 0 for x in parityV)]
        cols_free0 = [j for j in range(N) if parityV[j] == 0 or T[j] == ORE and any(x == 1 for x in parityU)]
        cols_free1 = [j for j in range(N) if parityV[j] == 1 or T[j] == AND and any(x == 0 for x in parityU)]
        rows_need0 = [i for i in range(N) if S[i] == AND and parityU[i] == 0] if not cols_free0 else []
        rows_need1 = [i for i in range(N) if S[i] == ORE and parityU[i] == 1]
        cols_need0 = [j for j in range(N) if T[j] == AND and parityV[j] == 0] if not rows_free0 else []
        cols_need1 = [j for j in range(N) if T[j] == ORE and parityV[j] == 1]
        if rows_free1:
            for col in cols_need1:
                ans[rows_free1[0]][col] |= 1 << b
            cols_need1 = []
        if cols_free1:
            for row in rows_need1:
                ans[row][cols_free1[0]] |= 1 << b
            rows_need1 = []
        can &= not rows_need0 or any(T[j] == ORE for j in range(N))
        can &= not rows_need1 or any(T[j] == AND for j in range(N))
        can &= not cols_need0 or any(S[i] == ORE for i in range(N))
        can &= not cols_need1 or any(S[i] == AND for i in range(N))
        can &= not any(len(a) == 1 and len(b) > 0 or len(b) == 1 and len(a) > 0 for a, b in ((rows_need0, cols_need1), (rows_need1, cols_need0)))
        for rows, cols in ((rows_need0, cols_need1), (cols_need0, rows_need1)):
            for ii, i in enumerate(rows):
                for jj, j in enumerate(cols):
                    ans[i][j] |= ((ii & 1) ^ (jj & 1)) << b
    if can:
        for row in ans:
            print(*row)
        # assert all(reduce(or_ if S[i] else and_, (ans[i][j] for j in range(N))) == U[i] for i in range(N))
        # assert all(reduce(or_ if T[j] else and_, (ans[i][j] for i in range(N))) == V[j] for j in range(N))
    else:
        print(-1)


# Generated by 1.1.6 https://github.com/kyuridenamida/atcoder-tools  (tips: You use the default template now. You can remove this line by using your custom template)
def main():
    N = int(sys.stdin.readline())  # type: int
    S = [int(x) for x in sys.stdin.readline().split()]  # type: "List[int]"
    T = [int(x) for x in sys.stdin.readline().split()]  # type: "List[int]"
    U = [int(x) for x in sys.stdin.readline().split()]  # type: "List[int]"
    V = [int(x) for x in sys.stdin.readline().split()]  # type: "List[int]"
    solve(N, S, T, U, V)

if __name__ == '__main__':
    from time import time
    start = time()
    main()
    end = time()
    print(end - start, file=sys.stderr)

Submission status: Wrong Answer

Solution code:
#!/usr/bin/env python3
import sys


def solve(N: int, S: "List[int]", T: "List[int]", U: "List[int]", V: "List[int]"):
    AND, ORE = 0, 1
    ans = [[0 for j in range(N)] for i in range(N)]
    can = True
    for b in range(64):
        parityU = [(x >> b) & 1 for x in U]
        parityV = [(x >> b) & 1 for x in V]
        for i in range(N):
            for j in range(N):
                if parityU[i] == parityV[j]:
                    ans[i][j] |= parityU[i] << b
                if S[i] == AND and parityU[i] == 1 or T[j] == AND and parityV[j] == 1:
                    ans[i][j] |= 1 << b
                can &= not (S[i] == ORE and parityU[i] == 0 and T[j] == AND and parityV[j] == 1)
                can &= not (S[i] == AND and parityU[i] == 1 and T[j] == ORE and parityV[j] == 0)
        rows_need0 = [i for i in range(N) if S[i] == AND and parityU[i] == 0] if all(parityV[j] == 1 for j in range(N)) else []
        rows_need1 = [i for i in range(N) if S[i] == ORE and parityU[i] == 1] if all(parityV[j] == 0 for j in range(N)) else []
        cols_need0 = [j for j in range(N) if T[j] == AND and parityV[j] == 0] if all(parityU[i] == 1 for i in range(N)) else []
        cols_need1 = [j for j in range(N) if T[j] == ORE and parityV[j] == 1] if all(parityU[i] == 0 for i in range(N)) else []
        can &= not rows_need0 or any(T[j] == ORE for j in range(N))
        can &= not rows_need1 or any(T[j] == AND for j in range(N))
        can &= not cols_need0 or any(S[i] == ORE for i in range(N))
        can &= not cols_need1 or any(S[i] == AND for i in range(N))
        can &= not any(len(a) == 1 and len(b) > 0 or len(b) == 1 and len(a) > 0 for a, b in ((rows_need0, cols_need1), (rows_need1, cols_need0)))
        for rows, cols in ((rows_need0, cols_need1), (cols_need0, rows_need1)):
            for ii, i in enumerate(rows):
                for jj, j in enumerate(cols):
                    ans[i][j] |= ((ii & 1) ^ (jj & 1)) << b
    if can:
        for row in ans:
            print(*row)
    else:
        print(-1)


# Generated by 1.1.6 https://github.com/kyuridenamida/atcoder-tools  (tips: You use the default template now. You can remove this line by using your custom template)
def main():
    N = int(sys.stdin.readline())  # type: int
    S = [int(x) for x in sys.stdin.readline().split()]  # type: "List[int]"
    T = [int(x) for x in sys.stdin.readline().split()]  # type: "List[int]"
    U = [int(x) for x in sys.stdin.readline().split()]  # type: "List[int]"
    V = [int(x) for x in sys.stdin.readline().split()]  # type: "List[int]"
    solve(N, S, T, U, V)

if __name__ == '__main__':
    main()

Submission status: Wrong Answer

Solution code:
#!/usr/bin/env python3
import sys


def solve(N: int, S: "List[int]", T: "List[int]", U: "List[int]", V: "List[int]"):
    AND, ORE = 0, 1
    ans = [[0 for j in range(N)] for i in range(N)]
    can = True
    for b in range(64):
        def parity(x):
            return (x >> b) & 1
        for i in range(N):
            for j in range(N):
                if parity(U[i]) == parity(V[j]):
                    ans[i][j] |= parity(U[i]) << b
                for res, par in ((S[i], parity(U[i])), (T[j], parity(V[j]))):
                    if res == ORE and par == 0:
                        ans[i][j] &= ~(1 << b)
                    if res == AND and par == 1:
                        ans[i][j] |= 1 << b
                can &= not (S[i] == ORE and parity(U[i]) == 0 and T[j] == AND and parity(V[j]) == 1)
                can &= not (S[i] == AND and parity(U[i]) == 1 and T[j] == ORE and parity(V[j]) == 0)
        if can:
            rows_need0 = [i for i in range(N) if S[i] == AND and parity(U[i]) == 0] if all(parity(V[j]) == 1 for j in range(N)) else []
            rows_need1 = [i for i in range(N) if S[i] == ORE and parity(U[i]) == 1] if all(parity(V[j]) == 0 for j in range(N)) else []
            cols_need0 = [j for j in range(N) if T[j] == AND and parity(V[j]) == 0] if all(parity(U[i]) == 1 for i in range(N)) else []
            cols_need1 = [j for j in range(N) if T[j] == ORE and parity(V[j]) == 1] if all(parity(U[i]) == 0 for i in range(N)) else []
            can &= not rows_need0 or any(T[j] == ORE for j in range(N))
            can &= not rows_need1 or any(T[j] == AND for j in range(N))
            can &= not cols_need0 or any(S[i] == ORE for i in range(N))
            can &= not cols_need1 or any(S[i] == AND for i in range(N))
            can &= not any(len(a) == 1 and len(b) > 0 or len(b) == 1 and len(a) > 0 for a, b in ((rows_need0, cols_need1), (rows_need1, cols_need0)))
            for rows, cols in ((rows_need0, cols_need1), (cols_need0, rows_need1)):
                for ii, i in enumerate(rows):
                    for jj, j in enumerate(cols):
                        ans[i][j] |= ((ii & 1) ^ (jj & 1)) << b
    if can:
        for row in ans:
            print(*row)
    else:
        print(-1)


# Generated by 1.1.6 https://github.com/kyuridenamida/atcoder-tools  (tips: You use the default template now. You can remove this line by using your custom template)
def main():
    N = int(sys.stdin.readline())  # type: int
    S = [int(x) for x in sys.stdin.readline().split()]  # type: "List[int]"
    T = [int(x) for x in sys.stdin.readline().split()]  # type: "List[int]"
    U = [int(x) for x in sys.stdin.readline().split()]  # type: "List[int]"
    V = [int(x) for x in sys.stdin.readline().split()]  # type: "List[int]"
    solve(N, S, T, U, V)

if __name__ == '__main__':
    main()

Submission status: Wrong Answer

Solution code:
#!/usr/bin/env python3
import sys


def solve(N: int, S: "List[int]", T: "List[int]", U: "List[int]", V: "List[int]"):
    AND, ORE = 0, 1
    ans = [[0 for j in range(N)] for i in range(N)]
    can = True
    for b in range(64):
        def parity(x):
            return (x >> b) & 1
        for i in range(N):
            for j in range(N):
                if parity(U[i]) == parity(V[j]):
                    ans[i][j] |= parity(U[i]) << b
                for res, par in ((S[i], parity(U[i])), (T[j], parity(V[j]))):
                    if res == ORE and par == 0:
                        ans[i][j] &= ~(1 << b)
                    if res == AND and par == 1:
                        ans[i][j] |= 1 << b
                can &= not (S[i] == ORE and parity(U[i]) == 0 and T[j] == AND and parity(V[j]) == 1)
                can &= not (S[i] == AND and parity(U[i]) == 1 and T[j] == ORE and parity(V[j]) == 0)
        if can:
            rows_need0 = [i for i in range(N) if S[i] == AND and parity(U[i]) == 0] if all(parity(V[j]) == 1 for j in range(N)) else []
            rows_need1 = [i for i in range(N) if S[i] == ORE and parity(U[i]) == 1] if all(parity(V[j]) == 0 for j in range(N)) else []
            cols_need0 = [j for j in range(N) if T[j] == AND and parity(V[j]) == 0] if all(parity(U[i]) == 1 for i in range(N)) else []
            cols_need1 = [j for j in range(N) if T[j] == ORE and parity(V[j]) == 1] if all(parity(U[i]) == 0 for i in range(N)) else []
            can &= not rows_need0 or any(T[j] == ORE for j in range(N))
            can &= not rows_need1 or any(T[j] == AND for j in range(N))
            can &= not cols_need0 or any(S[i] == ORE for i in range(N))
            can &= not cols_need1 or any(S[i] == AND for i in range(N))
            can &= not any(len(a) == 1 and len(b) > 0 or len(b) == 1 and len(a) > 0 for a, b in ((rows_need0, cols_need1), (rows_need1, cols_need0)))
            for rows, cols in ((rows_need0, cols_need1), (cols_need0, rows_need1)):
                for ii, i in enumerate(rows):
                    for jj, j in enumerate(cols):
                        ans[i][j] |= ((ii & 1) ^ (jj & 1)) << b
    if can:
        for row in ans:
            print(*row)
    else:
        print(-1)


# Generated by 1.1.6 https://github.com/kyuridenamida/atcoder-tools  (tips: You use the default template now. You can remove this line by using your custom template)
def main():
    def iterate_tokens():
        for line in sys.stdin:
            for word in line.split():
                yield word
    tokens = iterate_tokens()
    N = int(next(tokens))  # type: int
    S = [int(next(tokens)) for _ in range(N)]  # type: "List[int]"
    T = [int(next(tokens)) for _ in range(N)]  # type: "List[int]"
    U = [int(next(tokens)) for _ in range(N)]  # type: "List[int]"
    V = [int(next(tokens)) for _ in range(N)]  # type: "List[int]"
    solve(N, S, T, U, V)

if __name__ == '__main__':
    main()

Submission status: Wrong Answer

Solution code:
import sys
input = sys.stdin.readline
sys.setrecursionlimit(10**8)
mod = 10**9+7

def main():
    n = int(input())
    ans = [[0 for _ in range(n)] for _ in range(n)]
    s = list(map(int, input().split()))
    t = list(map(int, input().split()))
    u = list(map(int, input().split()))
    v = list(map(int, input().split()))
    for i in range(n):
        if not s[i]:
            for j in range(n):
                ans[i][j] = ans[i][j]|u[i]
        if not t[i]:   
            for j in range(n):
                ans[j][i] = ans[j][i]|v[i]
    for i in range(n):
        for j in range(n):
            if (u[i] & v[j]):
                ans[i][j] = ans[i][j]|(u[i]&v[j])


    for i in range(n):
        xs = 0
        for j in range(n):
            xs = xs|ans[i][j]
        if (xs&v[i]) == u[i]:
            continue
        up = u[i] - (xs&u[i])
        for j in range(n):
            if not up:
                break
            if v[j] == 1:
                continue
            xm = ans[i][0]
            for e in range(n):
                if i == e:
                    continue
                xm = xm&ans[e][j]
            diff = (ans[i][j]|up) - (ans[i][j]&up)
            if t[i]:
                ans[i][j] += ((diff|xm) - (diff&xm))&v[i]
                up -= ((diff|xm) - (diff&xm))&v[i]
            else:                
                ans[i][j] += (diff|xm) - (diff&xm)
                up -= (diff|xm) - (diff&xm)
        if up:
            print(-1)
            return

    for j in range(n):
        ys = 0
        for i in range(n):
            ys = ys|ans[i][j]
        if (ys&u[i]) == v[i]:
            continue
        up = v[j] - (ys&v[j])
        for i in range(n):
            if not up:
                break
            if u[i] == 1:
                continue
            ym = ans[i][0]
            for e in range(n):
                if j == e:
                    continue
                ym = ym&ans[i][e]
            diff = (ans[i][j]|up) - (ans[i][j]&up)
            if s[i]:
                ans[i][j] += ((diff|ym) - (diff&ym))&u[i]
                up -= ((diff|ym) - (diff&ym))&u[i]
            else:                
                ans[i][j] += (diff|ym) - (diff&ym)
                up -= (diff|ym) - (diff&ym)
        if up:
            print(-1)
            return

    for i in range(n):
        check_xs = 0
        check_ys = 0
        check_xm = ans[i][0]
        check_ym = ans[0][i]
        for j in range(n):
            check_xs = check_xs|ans[i][j]
            check_ys = check_ys|ans[j][i]
            check_xm = check_xm&ans[i][j]
            check_ym = check_ym&ans[j][i]
        if s[i] and u[i] != check_xs:
            print(-1)
            return       
        if t[i] and v[i] != check_ys:
            print(-1)
            return       
        if not s[i] and u[i] != check_xm:
            print(-1)
            return       
        if not t[i] and v[i] != check_ym:
            print(-1)
            return       
    for i in range(n):
        print(*ans[i])

if __name__ == "__main__":
    main()

Submission status: Wrong Answer

Solution code:
import sys
input = sys.stdin.readline
sys.setrecursionlimit(10**8)
mod = 10**9+7

def main():
    n = int(input())
    ans = [[0 for _ in range(n)] for _ in range(n)]
    s = list(map(int, input().split()))
    t = list(map(int, input().split()))
    u = list(map(int, input().split()))
    v = list(map(int, input().split()))
    for i in range(n):
        if not s[i]:
            for j in range(n):
                ans[i][j] = ans[i][j]|u[i]
        if not t[i]:   
            for j in range(n):
                ans[j][i] = ans[j][i]|v[i]
    for i in range(n):
        for j in range(n):
            if (u[i] & v[j]):
                ans[i][j] = ans[i][j]|(u[i]&v[j])
    
    for i in range(n):
        if not (s[i] and u[i]):
            continue
        xs = 0
        xm = ~0
        for j in range(n):
            xs = xs|ans[i][j]
            if i == j:
                continue
            xm = xm&ans[i][j]
        if (xs&u[i]) == u[i]:
            continue
        up = u[i] - (xs&u[i])
        for j in range(n):
            if not up:
                break
            if v[j] == 1:
                continue
            ans[i][j] += ((~ans[i][j])&up)&(~xm)
            up -= ((~ans[i][j])&up)&(~xm)

    for j in range(n):
        if not (t[j] and v[j]):
            continue
        ys = 0
        ym = ~0
        for i in range(n):
            ys = ys|ans[i][j]
            if i == j:
                continue
            ym = ym&ans[i][j]
        if (ys&u[i]) == v[i]:
            continue
        up = v[i] - (ys&v[i])
        for i in range(n):
            if not up:
                break
            if u[i] == 1:
                continue
            ans[i][j] += ((~ans[i][j])&up)&(~ym)
            up -= ((~ans[i][j])&up)&(~ym)
    for i in range(n):
        if s[i]:
            for j in range(n):
                if ans[i][j] & (~u[i]) != 0:
                    print(-1)
                    return
        if t[i]:   
            for j in range(n): 
                if ans[j][i] & (~v[i]) != 0:
                    print(-1)
                    return
    
    for i in range(n):
        print(*ans[i])
if __name__ == "__main__":
    main()

Submission status: Wrong Answer

Solution code:
from functools import reduce


def add_row(ans, n, i, k):
    for j in range(n):
        ans[i][j] |= k


def add_column(ans, n, j, k):
    for i in range(n):
        ans[i][j] |= k


def solve(n, sss, ttt, uuu, vvv):
    max_d = max(max(uuu).bit_length(), max(vvv).bit_length())
    ans = [[0] * n for _ in range(n)]

    for d in range(max_d):
        k = 1 << d
        ambiguous_i = []
        ambiguous_j = []
        filled_i = [False, False]
        filled_j = [False, False]
        for i, (s, u) in enumerate(zip(sss, uuu)):
            if s == 0:
                if u & k:
                    add_row(ans, n, i, k)
                    filled_i[1] = True
                else:
                    ambiguous_i.append((i, 0))
            else:
                if u & k:
                    ambiguous_i.append((i, 1))
                else:
                    filled_i[0] = True
        for j, (t, v) in enumerate(zip(ttt, vvv)):
            if t == 0:
                if v & k:
                    if filled_i[0]:
                        return -1
                    add_column(ans, n, j, k)
                    filled_j[1] = True
                else:
                    ambiguous_j.append((j, 0))
            else:
                if v & k:
                    ambiguous_j.append((j, 1))
                else:
                    if filled_i[1]:
                        return -1
                    filled_j[0] = True

        # print(d)
        # print(ans)
        # print(ambiguous_i)
        # print(ambiguous_j)

        # for i in range(n):
        #     print(*map('{:064b}'.format, ans[i]), end=' ')
        #     print('{:064b}'.format(uuu[i]))
        # print(*map('{:064b}'.format, vvv))
        # print(ambiguous_i, ambiguous_j)
        # print(filled_i, filled_j)
        # print()

        if len(ambiguous_i) == 0:
            amb = set(bj for j, bj in ambiguous_j)
            for bj in amb:
                if not filled_i[bj]:
                    return -1
        elif len(ambiguous_j) == 0:
            amb = set(bi for i, bi in ambiguous_i)
            for bi in amb:
                if not filled_j[bi]:
                    return -1
        elif len(ambiguous_i) == 1:
            i, bi = ambiguous_i[0]
            if filled_i[bi ^ 1]:
                if bi == 1:
                    for j, bj in ambiguous_j:
                        ans[i][j] |= k
            else:
                ok = False
                for j, bj in ambiguous_j:
                    if bj:
                        ans[i][j] |= k
                    if bi == bj:
                        ok = True
                if not ok:
                    return -1
        elif len(ambiguous_j) == 1:
            j, bj = ambiguous_j[0]
            if filled_j[bj ^ 1]:
                if bj == 1:
                    for i, bi in ambiguous_i:
                        ans[i][j] |= k
            else:
                ok = False
                for i, bi in ambiguous_i:
                    if bi:
                        ans[i][j] |= k
                    if bi == bj:
                        ok = True
                if not ok:
                    return -1
        else:
            for ii, (i, bi) in enumerate(ambiguous_i):
                for jj, (j, bj) in enumerate(ambiguous_j):
                    if (ii ^ jj) & 1:
                        ans[i][j] |= k

    return ans


def debug(n, sss, ttt, uuu, vvv, ans):
    from operator import or_, and_
    dbg = [row.copy() for row in ans]
    for i in range(n):
        func = and_ if sss[i] == 0 else or_
        dbg[i].append(reduce(func, dbg[i]))
        dbg[i].append(uuu[i])
    vertical = []
    correct = []
    for j in range(n):
        func = and_ if ttt[j] == 0 else or_
        vertical.append(reduce(func, (dbg[i][j] for i in range(n))))
        correct.append(vvv[j])
    dbg.append(vertical)
    dbg.append(correct)

    for row in dbg:
        print(*map('{:064b}'.format, row))


n = int(input())
sss = list(map(int, input().split()))
ttt = list(map(int, input().split()))
uuu = list(map(int, input().split()))
vvv = list(map(int, input().split()))

ans = solve(n, sss, ttt, uuu, vvv)
if ans == -1:
    print(ans)
else:
    for row in ans:
        print(*row)

Submission status: Wrong Answer

Solution code:
from functools import reduce


def add_row(ans, n, i, k):
    for j in range(n):
        ans[i][j] |= k


def add_column(ans, n, j, k):
    for i in range(n):
        ans[i][j] |= k


def solve(n, sss, ttt, uuu, vvv):
    max_d = max(max(uuu).bit_length(), max(vvv).bit_length())
    ans = [[0] * n for _ in range(n)]

    for d in range(max_d):
        k = 1 << d
        ambiguous_i = []
        ambiguous_j = []
        filled_i = [False, False]
        filled_j = [False, False]
        for i, (s, u) in enumerate(zip(sss, uuu)):
            if s == 0:
                if u & k:
                    add_row(ans, n, i, k)
                    filled_i[1] = True
                else:
                    ambiguous_i.append((i, 0))
            else:
                if u & k:
                    ambiguous_i.append((i, 1))
                else:
                    filled_i[0] = True
        for j, (t, v) in enumerate(zip(ttt, vvv)):
            if t == 0:
                if v & k:
                    if filled_i[0]:
                        return -1
                    add_column(ans, n, j, k)
                    filled_j[1] = True
                else:
                    ambiguous_j.append((j, 0))
            else:
                if v & k:
                    ambiguous_j.append((j, 1))
                else:
                    if filled_i[1]:
                        return -1
                    filled_j[0] = True

        # print(d)
        # print(ans)
        # print(ambiguous_i)
        # print(ambiguous_j)

        # for i in range(n):
        #     print(*map('{:064b}'.format, ans[i]), end=' ')
        #     print('{:064b}'.format(uuu[i]))
        # print(*map('{:064b}'.format, vvv))
        # print()

        if len(ambiguous_i) == 0:
            amb = set(bj for j, bj in ambiguous_j)
            for bj in amb:
                if not filled_i[bj]:
                    return -1
        elif len(ambiguous_j) == 0:
            amb = set(bi for i, bi in ambiguous_i)
            for bi in amb:
                if not filled_j[bi]:
                    return -1
        elif len(ambiguous_i) == 1:
            i, bi = ambiguous_i[0]
            if filled_i[bi ^ 1]:
                if bi == 1:
                    add_row(ans, n, i, k)
            else:
                ok = False
                for j, bj in ambiguous_j:
                    if bj:
                        ans[i][j] |= k
                    if bi == bj:
                        ok = True
                if not ok:
                    return -1
        elif len(ambiguous_j) == 1:
            j, bj = ambiguous_j[0]
            if filled_j[bj ^ 1]:
                if bj == 1:
                    add_column(ans, n, j, k)
            else:
                ok = False
                for i, bi in ambiguous_i:
                    if bi:
                        ans[i][j] |= k
                    if bi == bj:
                        ok = True
                if not ok:
                    return -1
        else:
            for ii, (i, bi) in enumerate(ambiguous_i):
                for jj, (j, bj) in enumerate(ambiguous_j):
                    if (ii ^ jj) & 1:
                        ans[i][j] |= k

    return ans


def debug(n, sss, ttt, uuu, vvv, ans):
    from operator import or_, and_
    dbg = [row.copy() for row in ans]
    for i in range(n):
        func = and_ if sss[i] == 0 else or_
        dbg[i].append(reduce(func, dbg[i]))
        dbg[i].append(uuu[i])
    vertical = []
    correct = []
    for j in range(n):
        func = and_ if ttt[j] == 0 else or_
        vertical.append(reduce(func, (dbg[i][j] for i in range(n))))
        correct.append(vvv[j])
    dbg.append(vertical)
    dbg.append(correct)

    for row in dbg:
        print(*map('{:064b}'.format, row))


n = int(input())
sss = list(map(int, input().split()))
ttt = list(map(int, input().split()))
uuu = list(map(int, input().split()))
vvv = list(map(int, input().split()))

ans = solve(n, sss, ttt, uuu, vvv)
if ans == -1:
    print(ans)
else:
    for row in ans:
        print(*row)

Submission status: Wrong Answer

Solution code:
from functools import reduce


def add_row(ans, n, i, k):
    for j in range(n):
        ans[i][j] |= k


def add_column(ans, n, j, k):
    for i in range(n):
        ans[i][j] |= k


def solve(n, sss, ttt, uuu, vvv):
    max_d = max(max(uuu).bit_length(), max(vvv).bit_length())
    ans = [[0] * n for _ in range(n)]

    for d in range(max_d):
        k = 1 << d
        ambiguous_i = []
        ambiguous_j = []
        filled_i = [False, False]
        filled_j = [False, False]
        for i, (s, u) in enumerate(zip(sss, uuu)):
            if s == 0:
                if u & k:
                    add_row(ans, n, i, k)
                    filled_i[1] = True
                else:
                    ambiguous_i.append((i, 0))
            else:
                if u & k:
                    ambiguous_i.append((i, 1))
                else:
                    filled_i[0] = True
        for j, (t, v) in enumerate(zip(ttt, vvv)):
            if t == 0:
                if v & k:
                    if filled_i[0]:
                        return -1
                    add_column(ans, n, j, k)
                    filled_j[1] = True
                else:
                    ambiguous_j.append((j, 0))
            else:
                if v & k:
                    ambiguous_j.append((j, 1))
                else:
                    if filled_i[1]:
                        return -1
                    filled_j[0] = True

        # print(d)
        # print(ans)
        # print(ambiguous_i)
        # print(ambiguous_j)

        # for i in range(n):
        #     print(*map('{:064b}'.format, ans[i]), end=' ')
        #     print('{:064b}'.format(uuu[i]))
        # print(*map('{:064b}'.format, vvv))
        # print()

        if len(ambiguous_i) == 0:
            amb = set(bj for j, bj in ambiguous_j)
            for bj in amb:
                if not filled_i[bj]:
                    return -1
        elif len(ambiguous_j) == 0:
            amb = set(bi for i, bi in ambiguous_i)
            for bi in amb:
                if not filled_j[bi]:
                    return -1
        elif len(ambiguous_i) == 1:
            i, bi = ambiguous_i[0]
            if filled_i[bi ^ 1]:
                if bi == 1:
                    add_row(ans, n, i, k)
            else:
                ok = False
                for j, bj in ambiguous_j:
                    if bj:
                        ans[i][j] += k
                    if bi == bj:
                        ok = True
                if not ok:
                    return -1
        elif len(ambiguous_j) == 1:
            j, bj = ambiguous_j[0]
            if filled_j[bj ^ 1]:
                if bj == 1:
                    add_column(ans, n, j, k)
            else:
                ok = False
                for i, bi in ambiguous_i:
                    if bi:
                        ans[i][j] += k
                    if bi == bj:
                        ok = True
                if not ok:
                    return -1
        else:
            for ii, (i, bi) in enumerate(ambiguous_i):
                for jj, (j, bj) in enumerate(ambiguous_j):
                    if (ii ^ jj) & 1:
                        ans[i][j] += k

    return ans


def debug(n, sss, ttt, uuu, vvv, ans):
    from operator import or_, and_
    dbg = [row.copy() for row in ans]
    for i in range(n):
        func = and_ if sss[i] == 0 else or_
        dbg[i].append(reduce(func, dbg[i]))
        dbg[i].append(uuu[i])
    vertical = []
    correct = []
    for j in range(n):
        func = and_ if ttt[j] == 0 else or_
        vertical.append(reduce(func, (dbg[i][j] for i in range(n))))
        correct.append(vvv[j])
    dbg.append(vertical)
    dbg.append(correct)

    for row in dbg:
        print(*map('{:064b}'.format, row))


n = int(input())
sss = list(map(int, input().split()))
ttt = list(map(int, input().split()))
uuu = list(map(int, input().split()))
vvv = list(map(int, input().split()))

ans = solve(n, sss, ttt, uuu, vvv)
if ans == -1:
    print(ans)
else:
    for row in ans:
        print(*row)