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 Rust (1.42.0) (judge verdict: Accepted)

use proconio::{input, fastout};
use std::cmp::max;
use itertools::Itertools;


#[fastout]
fn main() {
    input! {
        n: usize,
        sss: [u8; n],
        ttt: [u8; n],
        uuu: [u64; n],
        vvv: [u64; n],
    }

    let mut ans = vec![vec![0; n]; n];
    let mut k = 1u64;

    let max_uv: u64 = *max(uuu.iter().max().unwrap(), vvv.iter().max().unwrap());

    while k <= max_uv && k != 0 {
        let mut ambiguous: Vec<Vec<Vec<usize>>> = vec![vec![vec![]; 2]; 2];
        let mut filled = [[false, false], [false, false]];
        for i in 0..n {
            let s = sss[i] as usize;
            let u = (uuu[i] & k != 0) as usize;
            if s ^ u == 1 {
                if u == 1 { for j in 0..n { ans[i][j] |= k } }
                filled[0][u] = true;
            } else {
                ambiguous[0][u].push(i);
            }
        }
        for j in 0..n {
            let t = ttt[j] as usize;
            let v = (vvv[j] & k != 0) as usize;
            if t ^ v == 1 {
                if filled[0][v ^ 1] {
                    println!("-1");
                    return;
                }
                if v == 1 { for i in 0..n { ans[i][j] |= k } }
                filled[1][v] = true;
            } else {
                ambiguous[1][v].push(j);
            }
        }

        let amb_i_cnt = ambiguous[0][0].len() + ambiguous[0][1].len();
        let amb_j_cnt = ambiguous[1][0].len() + ambiguous[1][1].len();

        if amb_i_cnt == 0 || amb_j_cnt == 0 {
            let ij = if amb_i_cnt == 0 { 0 } else { 1 };
            for b in 0..2 {
                if !ambiguous[ij ^ 1][b].is_empty() && !filled[ij][b] {
                    println!("-1");
                    return;
                }
            }
        } else if amb_i_cnt == 1 {
            let b = if ambiguous[0][0].len() == 1 { 0 } else { 1 };
            let i = &ambiguous[0][b][0];
            if ambiguous[1][b].len() > 0 || filled[1][b] {
                for j in &ambiguous[1][1] { ans[*i][*j] |= k; }
            } else if filled[0][b ^ 1] {
                if b == 1 { for j in &ambiguous[1][b ^ 1] { ans[*i][*j] |= k; } }
            } else {
                println!("-1");
                return;
            }
        } else if amb_j_cnt == 1 {
            let b = if ambiguous[1][0].len() == 1 { 0 } else { 1 };
            let j = &ambiguous[1][b][0];
            if ambiguous[0][b].len() > 0 || filled[0][b] {
                for i in &ambiguous[0][1] { ans[*i][*j] |= k; }
            } else if filled[1][b ^ 1] {
                if b == 1 { for i in &ambiguous[0][b ^ 1] { ans[*i][*j] |= k; } }
            } else {
                println!("-1");
                return;
            }
        } else {
            let mut amb0 = ambiguous[0][0].clone();
            let mut amb1 = ambiguous[1][0].clone();
            amb0.append(&mut ambiguous[0][1]);
            amb1.append(&mut ambiguous[1][1]);
            for (bi, i) in amb0.iter().enumerate() {
                for (bj, j) in amb1.iter().enumerate() {
                    if (bi ^ bj) & 1 == 1 { ans[*i][*j] |= k; }
                }
            }
        }

        k <<= 1;
    }

    for row in ans {
        println!("{}", row.iter().join(" "));
    }
}