# Original solution
#!usr/bin/env python3
from collections import defaultdict
from collections import deque
from heapq import heappush, heappop
import sys
import math
import bisect
import random
def LI(): return list(map(int, sys.stdin.readline().split()))
def I(): return int(sys.stdin.readline())
def LS():return list(map(list, sys.stdin.readline().split()))
def S(): return list(sys.stdin.readline())[:-1]
def IR(n):
    l = [None for i in range(n)]
    for i in range(n):l[i] = I()
    return l
def LIR(n):
    l = [None for i in range(n)]
    for i in range(n):l[i] = LI()
    return l
def SR(n):
    l = [None for i in range(n)]
    for i in range(n):l[i] = S()
    return l
def LSR(n):
    l = [None for i in range(n)]
    for i in range(n):l[i] = LS()
    return l
sys.setrecursionlimit(1000000)
mod = 1000000007

#A
def A():
    a,b,t = LI()
    k = t//a
    print((k*b))
    return

#B
def B():
    n = I()
    v = LI()
    c = LI()
    ans = 0
    for i in range(n):
        if v[i] > c[i]:
            ans += (v[i]-c[i])
    print(ans)
    return

#C
def C():
    def gcd(a,b):
        if a == 0:
            return b
        return gcd(b%a, a)
    n = I()
    a = LI()
    m = math.ceil(n**0.5)
    f = [0 for i in range(m)]
    for i in range(m):
        b = a[m*i:min(n,m*(i+1))]
        if b:
            g = b[0]
            for j in b[1:]:
                g = gcd(g,j)
            f[i] = g
        else:
            f.pop(-1)
    ans = 1
    for i in range(n):
        j = i//m
        c = f[:j]+f[j+1:]+a[m*j:i]+a[i+1:min(n,m*(j+1))]
        g = c[0]
        for k in c[1:]:
            g = gcd(g, k)
        ans = max(ans,g)
    print(ans)
    return

#D
def D():
    n = I()
    a = LI()
    k = 0
    for i in a:
        if i < 0:
            k += 1
    ans = 0
    m = float("inf")
    for i in a:
        ans += abs(i)
        m = min(m,abs(i))
    if k%2:
        ans -= 2*m
    print(ans)
    return


#Solve
if __name__ == "__main__":
    C()


# Optimized solution
import operator
class SegmentTree:
    def __init__(self, size, default, op = operator.add):
        self.size = 1
        while self.size < size:
            self.size *= 2
        self.dat = [default]*(self.size*2-1)
        self.op = op

    def update(self, i, x):
        i += self.size - 1
        self.dat[i] = x
        while i > 0:
            i = (i - 1) // 2
            self.dat[i] = self.op(self.dat[i*2+1], self.dat[i*2+2])

    def add(self, i, x):
        i += self.size - 1
        self.dat[i] = self.op(self.dat[i], x)
        while i > 0:
            i = (i - 1) // 2
            self.dat[i] = self.op(self.dat[i], x)

    def get(self, a, b, k = None, l = None, r = None):
        if k is None:
            k = 0
            l = 0
            r = self.size

        if r <= a or b <= l:
            return None

        if a <= l and r <= b:
            return self.dat[k]

        res_l = self.get(a, b, k*2+1, l, (l+r)//2)
        res_r = self.get(a, b, k*2+2, (l+r)//2, r)
        if res_l is None:
            return res_r
        if res_r is None:
            return res_l
        return self.op(res_l, res_r)
def gcd(a,b):
    if a == 0:
        return b
    if b == 0:
        return a
    return gcd(b%a, a)

n = int(eval(input()))
a = list(map(int, input().split()))
seg = SegmentTree(n,0,gcd)
for i in range(n):
    seg.update(i,a[i])
ans = 1
for i in range(n):
    seg.update(i,0)
    ans = max(ans, seg.get(0,n))
    seg.update(i,a[i])
print(ans)