#from sympy import*
import re
def isprime(n):
return all(n%i for i in range(2,int(n**.5)+1))
def tree(n,hs=(0,)):
if isprime(n):return str(n)
A=max(z for z in range(1,int(n**.5)+1)if n%z<1)
B=n//A
x=tree(A)
y=tree(B)
xs=[i for i in range(len(x))if re.match('^[0-9 ]+$',x[i])]
ys=[j for j in range(len(y))if re.match('^[0-9 ]+$',y[j])]
ht=max(xs,ys)
hv=hs[1:]or[k[1]-k[0]for k in zip(ht[:-1],ht[1:])]
x=tree(A,hv)
y=tree(B,hv)
p=x[0][::-1].index(str(A)[-1])+1-(len(str(A))>1)
q=y[0].index(str(B)[0])+1-(len(str(B))>1)
h = hs[0]or 2-(p+q-len(str(n)))%2
# while spacing is too small
incorrect_spacing = True
while incorrect_spacing:
h+=2
R=[]
z=[]
for i in range(ht[-1]+1):
a=i<len(x)and x[i]or" "*len(x[0])
b=i<len(y)and y[i]or" "*len(y[0])
R+=a+" "*h+b,
if i in ht:z+=a+" "*h+b,
incorrect_spacing=not all(re.match('(\d| +)*$',s)for s in z)
# until spacing is too small
correct_spacing = True
while correct_spacing and h>-1:
h-=2
R=[]
z=[]
for i in range(ht[-1]+1):
a=i<len(x)and x[i]or" "*len(x[0])
b=i<len(y)and y[i]or" "*len(y[0])
R+=a+" "*h+b,
if i in ht:z+=a+" "*h+b,
correct_spacing=all(re.match('(\d| +)*$',s)for s in z)
h+=2 # correct it again after the spacing gets too small
# and now to put the root down
R=[]
total = len(x[0])+h+len(y[0])
for i in range(ht[-1]+1):
a=i<len(x)and x[i]or" "*len(x[0])
b=i<len(y)and y[i]or" "*len(y[0])
R+=a+" "*h+b,
v = p+q+h-len(str(n))-(len(str(A))>1)-(len(str(B))>1)
for i in range(v//2):
R=[" "*(len(x[0])-p+i)+"/"+" "*(p+q+h-2*i-2)+"\\"+" "*(len(y[0])-q+i)]+R
R=[" "*(len(x[0])-p+v//2)+str(n)+" "*(len(y[0])-q+v//2)]+R
return R
for i in tree(16):
print(i)
I2Zyb20gc3ltcHkgaW1wb3J0KgppbXBvcnQgcmUKCmRlZiBpc3ByaW1lKG4pOgoJcmV0dXJuIGFsbChuJWkgZm9yIGkgaW4gcmFuZ2UoMixpbnQobioqLjUpKzEpKQoKZGVmIHRyZWUobixocz0oMCwpKToKICAgIGlmIGlzcHJpbWUobik6cmV0dXJuIHN0cihuKQogICAgQT1tYXgoeiBmb3IgeiBpbiByYW5nZSgxLGludChuKiouNSkrMSlpZiBuJXo8MSkKICAgIEI9bi8vQQogICAgCiAgICB4PXRyZWUoQSkKICAgIHk9dHJlZShCKQogICAgeHM9W2kgZm9yIGkgaW4gcmFuZ2UobGVuKHgpKWlmIHJlLm1hdGNoKCdeWzAtOSBdKyQnLHhbaV0pXQogICAgeXM9W2ogZm9yIGogaW4gcmFuZ2UobGVuKHkpKWlmIHJlLm1hdGNoKCdeWzAtOSBdKyQnLHlbal0pXQogICAgaHQ9bWF4KHhzLHlzKQogICAgaHY9aHNbMTpdb3Jba1sxXS1rWzBdZm9yIGsgaW4gemlwKGh0WzotMV0saHRbMTpdKV0KICAgIHg9dHJlZShBLGh2KQogICAgeT10cmVlKEIsaHYpCgogICAgcD14WzBdWzo6LTFdLmluZGV4KHN0cihBKVstMV0pKzEtKGxlbihzdHIoQSkpPjEpCiAgICBxPXlbMF0uaW5kZXgoc3RyKEIpWzBdKSsxLShsZW4oc3RyKEIpKT4xKQogICAgaCA9IGhzWzBdb3IgMi0ocCtxLWxlbihzdHIobikpKSUyCgogICAgIyB3aGlsZSBzcGFjaW5nIGlzIHRvbyBzbWFsbAogICAgaW5jb3JyZWN0X3NwYWNpbmcgPSBUcnVlCiAgICB3aGlsZSBpbmNvcnJlY3Rfc3BhY2luZzoKICAgICAgICBoKz0yCiAgICAgICAgUj1bXQogICAgICAgIHo9W10KICAgICAgICBmb3IgaSBpbiByYW5nZShodFstMV0rMSk6CiAgICAgICAgICAgIGE9aTxsZW4oeClhbmQgeFtpXW9yIiAiKmxlbih4WzBdKQogICAgICAgICAgICBiPWk8bGVuKHkpYW5kIHlbaV1vciIgIipsZW4oeVswXSkKICAgICAgICAgICAgUis9YSsiICIqaCtiLAogICAgICAgICAgICBpZiBpIGluIGh0OnorPWErIiAiKmgrYiwKICAgICAgICBpbmNvcnJlY3Rfc3BhY2luZz1ub3QgYWxsKHJlLm1hdGNoKCcoXGR8ICArKSokJyxzKWZvciBzIGluIHopCgogICAgIyB1bnRpbCBzcGFjaW5nIGlzIHRvbyBzbWFsbAogICAgY29ycmVjdF9zcGFjaW5nID0gVHJ1ZQogICAgd2hpbGUgY29ycmVjdF9zcGFjaW5nIGFuZCBoPi0xOgogICAgICAgIGgtPTIKICAgICAgICBSPVtdCiAgICAgICAgej1bXQogICAgICAgIGZvciBpIGluIHJhbmdlKGh0Wy0xXSsxKToKICAgICAgICAgICAgYT1pPGxlbih4KWFuZCB4W2ldb3IiICIqbGVuKHhbMF0pCiAgICAgICAgICAgIGI9aTxsZW4oeSlhbmQgeVtpXW9yIiAiKmxlbih5WzBdKQogICAgICAgICAgICBSKz1hKyIgIipoK2IsCiAgICAgICAgICAgIGlmIGkgaW4gaHQ6eis9YSsiICIqaCtiLAogICAgICAgIGNvcnJlY3Rfc3BhY2luZz1hbGwocmUubWF0Y2goJyhcZHwgICspKiQnLHMpZm9yIHMgaW4geikKICAgIGgrPTIgIyBjb3JyZWN0IGl0IGFnYWluIGFmdGVyIHRoZSBzcGFjaW5nIGdldHMgdG9vIHNtYWxsCgogICAgIyBhbmQgbm93IHRvIHB1dCB0aGUgcm9vdCBkb3duCiAgICBSPVtdCiAgICB0b3RhbCA9IGxlbih4WzBdKStoK2xlbih5WzBdKQogICAgZm9yIGkgaW4gcmFuZ2UoaHRbLTFdKzEpOgogICAgICAgIGE9aTxsZW4oeClhbmQgeFtpXW9yIiAiKmxlbih4WzBdKQogICAgICAgIGI9aTxsZW4oeSlhbmQgeVtpXW9yIiAiKmxlbih5WzBdKQogICAgICAgIFIrPWErIiAiKmgrYiwKICAgIHYgPSBwK3EraC1sZW4oc3RyKG4pKS0obGVuKHN0cihBKSk+MSktKGxlbihzdHIoQikpPjEpCiAgICBmb3IgaSBpbiByYW5nZSh2Ly8yKToKICAgICAgICBSPVsiICIqKGxlbih4WzBdKS1wK2kpKyIvIisiICIqKHArcStoLTIqaS0yKSsiXFwiKyIgIioobGVuKHlbMF0pLXEraSldK1IKICAgIFI9WyIgIioobGVuKHhbMF0pLXArdi8vMikrc3RyKG4pKyIgIioobGVuKHlbMF0pLXErdi8vMildK1IKICAgIHJldHVybiBSCiAgICAKZm9yIGkgaW4gdHJlZSgxNik6CglwcmludChpKQ==