Problem:
Score : 500 points

Problem Statement

We have N integers. The i-th number is A_i.

\{A_i\} is said to be pairwise coprime when GCD(A_i,A_j)=1 holds for every pair (i, j) such that 1\leq i < j \leq N.

\{A_i\} is said to be setwise coprime when \{A_i\} is not pairwise coprime but GCD(A_1,\ldots,A_N)=1.

Determine if \{A_i\} is pairwise coprime, setwise coprime, or neither.

Here, GCD(\ldots) denotes greatest common divisor.

Constraints

2 \leq N \leq 10^6

1 \leq A_i\leq 10^6

Input

Input is given from Standard Input in the following format:

N
A_1 \ldots A_N

Output

If \{A_i\} is pairwise coprime, print pairwise coprime; if \{A_i\} is setwise coprime, print setwise coprime; if neither, print not coprime.

Sample Input 1

3
3 4 5

Sample Output 1

pairwise coprime

GCD(3,4)=GCD(3,5)=GCD(4,5)=1, so they are pairwise coprime.

Sample Input 2

3
6 10 15

Sample Output 2

setwise coprime

Since GCD(6,10)=2, they are not pairwise coprime. However, since GCD(6,10,15)=1, they are setwise coprime.

Sample Input 3

3
6 10 16

Sample Output 3

not coprime

GCD(6,10,16)=2, so they are neither pairwise coprime nor setwise coprime.

Solution in Rust (1.42.0) (judge verdict: Wrong Answer)

extern crate num_traits;
/// input macro from https://qiita.com/tanakh/items/1ba42c7ca36cd29d0ac8
macro_rules ! read_value {($ next : expr , ($ ($ t : tt ) ,* ) ) => {($ (read_value ! ($ next , $ t ) ) ,* ) } ; ($ next : expr , [$ t : tt ; $ len : expr ] ) => {(0 ..$ len ) . map (| _ | read_value ! ($ next , $ t ) ) . collect ::< Vec < _ >> () } ; ($ next : expr , chars ) => {read_value ! ($ next , String ) . chars () . collect ::< Vec < char >> () } ; ($ next : expr , usize1 ) => {read_value ! ($ next , usize ) - 1 } ; ($ next : expr , $ t : ty ) => {$ next () . parse ::<$ t > () . expect ("Parse error" ) } ; }
macro_rules ! input_inner {($ next : expr ) => {} ; ($ next : expr , ) => {} ; ($ next : expr , $ var : ident : $ t : tt $ ($ r : tt ) * ) => {let $ var = read_value ! ($ next , $ t ) ; input_inner ! {$ next $ ($ r ) * } } ; }
macro_rules ! input {(source = $ s : expr , $ ($ r : tt ) * ) => {let mut iter = $ s . split_whitespace () ; let mut next = || {iter . next () . unwrap () } ; input_inner ! {next , $ ($ r ) * } } ; ($ ($ r : tt ) * ) => {let stdin = std :: io :: stdin () ; let mut bytes = std :: io :: Read :: bytes (std :: io :: BufReader :: new (stdin . lock () ) ) ; let mut next = move || -> String {bytes . by_ref () . map (| r | r . unwrap () as char ) . skip_while (| c | c . is_whitespace () ) . take_while (| c |! c . is_whitespace () ) . collect () } ; input_inner ! {next , $ ($ r ) * } } ; }

macro_rules ! rough_print {($ x : expr $ (, $ s : expr ) * ) => {print ! ("{:?}" , $ x ) ; $ (print ! (", {:?}" , $ s ) ; ) * println ! ("" ) ; } ; }

fn gcd<T>(a: T, b: T) -> T
where
    T: num_traits::PrimInt,
{
    if b == T::from(0).unwrap() {
        a
    }
    else {
        gcd(b, a % b)
    }
}
fn gcd_list<T>(list: &[T]) -> T
where
    T: num_traits::PrimInt,
{
    list.iter().fold(list[0], |a, &b| gcd(a, b))
}

fn solve() {
    input!(n: usize, a: [usize; n]);

    if gcd_list(&a) != 1 {
        println!("not coprime");
        return;
    }

    let a_max = *(a.iter().max().unwrap());
    let mut elist: Vec<usize> = (0..=a_max).collect();
    for i in 2..=a_max {
        if elist[i] == i {
            let mut tmp = i;
            while tmp < a_max {
                if elist[tmp] > i {
                    elist[tmp] = i;
                }
                tmp += i;
            }
        }
    }

    let mut divided = vec![false; a_max + 1];
    for &_ai in &a {
        let mut ai = _ai;
        if elist[ai] == ai {
            if divided[ai] {
                println!("setwise coprime");
                return;
            }

            divided[ai] = true;
        }

        while elist[ai] != ai {
            let p = elist[ai];

            while elist[ai] == p {
                ai /= p;
            }

            if divided[p] {
                println!("setwise coprime");
                return;
            }

            divided[p] = true;
        }
    }

    println!("pairwise coprime");
}

fn main() {
    std::thread::Builder::new()
        .name("solve".into())
        .stack_size(256 * 1024 * 1024)
        .spawn(solve)
        .unwrap()
        .join()
        .unwrap();
}