FA-79926 / Typography line breaking / Open access
Pattern-based hyphenation: left hyphen minimum · case 01
Words are hyphenated one letter too late at the start.
ROOT CAUSE
The left minimum uses i > lmin instead of i >= lmin.
VERIFIED REPAIR
Allow a hyphen when at least lefthyphenmin letters precede it.
Unsuccessful approach: Using i >= lmin - 1 now allows too-short prefixes.
Case contract
Input [word, patterns, exceptions, lefthyphenmin, righthyphenmin]. An exception (hyphenated, lowercase) matching the lowercased word dictates the hyphens and keeps the word's own letters. Otherwise the lowercased word is padded with dots, every substring pattern contributes its digits and the maximum digit per gap wins; odd values allow a hyphen. A hyphen before letter i needs i>=lefthyphenmin and len-i>=righthyphenmin. Return the word with "-" inserted.
Why this case matters
Line breaking decides where paragraphs wrap on screen and in print; a wrong decision point shifts every following line.
1 / The failure
Exit 1"""Failure Map reference implementation. Python standard library only."""
import json
N = 1
observations = []
def solve(x):
word, patterns, exceptions, lmin, rmin = x
low = word.lower()
for e in exceptions:
if e.replace('-', '') == low:
out, count = '', 0
for c in e:
if c == '-':
out += '-'
else:
out += word[count]
count += 1
return out
table = {}
for p in patterns:
letters = ''
vals = [0]
for c in p:
if c.isdigit():
vals[-1] = int(c)
else:
letters += c
vals.append(0)
table[letters] = vals
dotted = '.' + low + '.'
score = [0] * (len(dotted) + 1)
for s in range(len(dotted)):
for e in range(s + 1, len(dotted) + 1):
vals = table.get(dotted[s:e])
if vals:
for k, v in enumerate(vals):
score[s + k] = max(score[s + k], v)
points = [i for i in range(1, len(word)) if score[i + 1] % 2 == 1 and i > lmin and len(word) - i >= rmin]
out = ''
for i, c in enumerate(word):
if i in points:
out += '-'
out += c
return out
def check(label, actual, expected):
observations.append({"check": label, "actual": actual, "expected": expected, "passed": actual == expected})
fixtures = [[('left minimum boundary', ['excellent', ['.ta4', 'a1b', 'b2l', '1ble', 'hy3ph', 'he2n', 'hena4', 'hen5at', '1na', 'n2at', '1tio', '2io', 'o2n', 'pu2', 'ter1', '1m', 'ex1', 'e1c', 'c2ce', 'con1', 'ment1', '4ing.', 'n1g', '.re1', 'gr2', '3ty.', 'li1', '1ca', 'ca1t', 'at1', 'io3n.', 'r1r', 'm1m', 'l1l', 't1t', 's1s', 'a2n', 'an1d', '5nd.', '1p', 'p2h', '1q', '.un1', 'e2x', 'x1c', '2mp', 'om1'], [], 2, 3], 'ex-cel-lent'), ('regression: left hyphen minimum', ['Commitment', ['io3n.', 'hen5at', '3ty.', '1p', 'ca1t', '.ta4', 'x1c', 'n2at', 'm1m', 'e1c', 'r1r', 'hy3ph', 'ter1', '.un1', 's1s', 'hena4', '2mp', 'p2h', 'o2n', 'at1', '1q', 'he2n', '1m', 'ment1', '1ca', 'l1l', '.re1', '2io', '5nd.', 'c2ce', 'an1d', 'li1', 'b2l', 'a2n', 'om1', 'n1g', '1ble', 'pu2', 't1t', 'ex1', '1na', '4ing.'], [], 3, 2], 'Com-mit-ment'), ('partial-repair probe', ['Categories', ['1ca', '.re1', '.un1', '2io', 'a1b', 'con1', 'p2h', 'li1', 'o2n', 'n1g', '3ty.', 'ca1t'], ['ex-cep-tion', 'pro-ject'], 3, 2], 'Categories'), ('regression: left hyphen minimum', ['Commitment', ['ex1', '.re1', 'io3n.', 'x1c', '1m', '1ble', 'con1', 'a2n', '3ty.', '1p', 'hen5at', 'p2h', 'an1d', 'hena4'], ['ex-cep-tion', 'ta-ble', 'pro-ject'], 3, 3], 'Com-mit-ment'), ('word-final pattern ing.', ['running', ['.ta4', 'a1b', 'b2l', '1ble', 'hy3ph', 'he2n', 'hena4', 'hen5at', '1na', 'n2at', '1tio', '2io', 'o2n', 'pu2', 'ter1', '1m', 'ex1', 'e1c', 'c2ce', 'con1', 'ment1', '4ing.', 'n1g', '.re1', 'gr2', '3ty.', 'li1', '1ca', 'ca1t', 'at1', 'io3n.', 'r1r', 'm1m', 'l1l', 't1t', 's1s', 'a2n', 'an1d', '5nd.', '1p', 'p2h', '1q', '.un1', 'e2x', 'x1c', '2mp', 'om1'], [], 2, 2], 'running'), ('lowercase exception', ['project', ['.ta4', 'a1b', 'b2l', '1ble', 'hy3ph', 'he2n', 'hena4', 'hen5at', '1na', 'n2at', '1tio', '2io', 'o2n', 'pu2', 'ter1', '1m', 'ex1', 'e1c', 'c2ce', 'con1', 'ment1', '4ing.', 'n1g', '.re1', 'gr2', '3ty.', 'li1', '1ca', 'ca1t', 'at1', 'io3n.', 'r1r', 'm1m', 'l1l', 't1t', 's1s', 'a2n', 'an1d', '5nd.', '1p', 'p2h', '1q', '.un1', 'e2x', 'x1c', '2mp', 'om1'], ['pro-ject'], 2, 3], 'pro-ject'), ('control layout', ['Categories', ['.ta4', 'c2ce', 's1s', 'x1c', 'p2h', '1p', 'pu2', 'o2n', 'r1r', 'io3n.', 'ment1', 'an1d', '3ty.', 'n1g', '.re1', '2mp', 'a1b', '1ca', 'li1'], ['ta-ble', 'gram-mar', 'pro-ject'], 2, 1], 'Categories'), ('control layout', ['Table', ['ex1', 'hy3ph', 'pu2', '.ta4', '4ing.', '1q', 'n2at', '1tio', '.re1', 'b2l', '2io', 'a1b'], ['ta-ble', 'mis-sis-sip-pi', 'pro-ject'], 2, 2], 'Ta-ble')], [('regression: left hyphen minimum', ['typesetting', ['ca1t', '.ta4', 'e1c', 'ment1', '1p', '1ble', 'p2h', 'n2at', 'a2n', '1tio', 'x1c', 'gr2', '2io', 'e2x', 'm1m', 'r1r', 'a1b', 'con1', 'io3n.', '.re1', 'l1l', '1ca', 'om1', 'hena4', '2mp', 't1t', 'li1'], ['gram-mar', 'pro-ject'], 2, 2], 'ty-peset-ting'), ('regression: left hyphen minimum', ['hyphenation', ['hy3ph', 'r1r', 'ment1', '.re1', 'li1', '1ble', 'hen5at', 't1t', '1m', 'c2ce', 'm1m'], [], 2, 2], 'hy-phen-ation'), ('partial-repair probe', ['understand', ['ca1t', 'l1l', 'an1d', 'n2at', 'a2n', 'gr2', 'c2ce', '3ty.', '1m', 'r1r', '1na', '2mp', 'he2n', '4ing.', 'ter1', 'a1b', 'om1', 'e1c', 'hen5at', 'n1g', '1ca', 'm1m', '2io', 'b2l', '.un1', 'pu2', 'hena4', 'o2n', '1p'], ['mis-sis-sip-pi', 'ta-ble'], 3, 2], 'understand'), ('partial-repair probe', ['Categories', ['t1t', 'ca1t', '1p', '1m', 'r1r', '1ca', '.ta4', 'hen5at', 'a1b', '2io', 'ex1', 'gr2', '1na', 'con1', 'li1', '1q', 'ter1', '.un1', 'io3n.', 'hy3ph', 's1s', 'c2ce', '1tio'], ['pro-ject'], 3, 2], 'Categories'), ('word-final pattern ing.', ['running', ['.ta4', 'a1b', 'b2l', '1ble', 'hy3ph', 'he2n', 'hena4', 'hen5at', '1na', 'n2at', '1tio', '2io', 'o2n', 'pu2', 'ter1', '1m', 'ex1', 'e1c', 'c2ce', 'con1', 'ment1', '4ing.', 'n1g', '.re1', 'gr2', '3ty.', 'li1', '1ca', 'ca1t', 'at1', 'io3n.', 'r1r', 'm1m', 'l1l', 't1t', 's1s', 'a2n', 'an1d', '5nd.', '1p', 'p2h', '1q', '.un1', 'e2x', 'x1c', '2mp', 'om1'], [], 2, 2], 'running'), ('left minimum boundary', ['excellent', ['.ta4', 'a1b', 'b2l', '1ble', 'hy3ph', 'he2n', 'hena4', 'hen5at', '1na', 'n2at', '1tio', '2io', 'o2n', 'pu2', 'ter1', '1m', 'ex1', 'e1c', 'c2ce', 'con1', 'ment1', '4ing.', 'n1g', '.re1', 'gr2', '3ty.', 'li1', '1ca', 'ca1t', 'at1', 'io3n.', 'r1r', 'm1m', 'l1l', 't1t', 's1s', 'a2n', 'an1d', '5nd.', '1p', 'p2h', '1q', '.un1', 'e2x', 'x1c', '2mp', 'om1'], [], 2, 3], 'ex-cel-lent'), ('control layout', ['table', ['c2ce', '3ty.', 'he2n', '2io', 's1s', '.un1', 'con1', 'hena4', '1p', 'ca1t', 'n2at', '4ing.', 'om1', 'ment1', 'a1b', 'a2n', 'gr2', 'p2h', '1tio', 'li1', 'ex1', '1ca', '1m', 'ter1'], ['ex-cep-tion'], 1, 1], 'ta-ble'), ('control layout', ['Exception', ['he2n', '.re1', '3ty.', 'e2x', 'n2at', 'e1c', '2mp', '1m', '.ta4', '2io', 'a1b', 'hen5at', '1ble', 'ex1', 'at1', 'an1d', 'ca1t', 'io3n.'], ['gram-mar', 'mis-sis-sip-pi'], 1, 2], 'Ex-ception')], [('regression: left hyphen minimum', ['typesetting', ['ex1', 'b2l', '1ble', 'hena4', 'pu2', 'e2x', '.un1', 'a1b', 'r1r', '5nd.', 'con1', 'io3n.', 'c2ce', '1q', 'n2at', 'ter1', 'l1l', '1na', 'o2n', 'hen5at', 'x1c', 's1s', '2io', 'an1d', 'a2n', 'hy3ph', '3ty.', 'n1g', 'at1', '1p', 'gr2', '4ing.', 't1t', '2mp', 'li1', 'ca1t', '1m', 'he2n', 'p2h', '1ca', 'ment1', '1tio', 'm1m', '.re1', 'om1', 'e1c', '.ta4'], [], 2, 3], 'ty-peset-ting'), ('regression: left hyphen minimum', ['grammar', ['c2ce', '5nd.', '1tio', '1m', 'a2n', '1q', 'gr2', 's1s', 'l1l', 'n2at', 'o2n', 'hy3ph', 'n1g', '1na', 'con1', 'e2x', '4ing.', 'at1', 't1t', 'pu2', '.re1', '2mp', 'ment1', 'e1c', 'r1r', '1ca', 'io3n.', 'ex1', 'li1', '.un1', 'x1c', 'a1b', 'p2h'], ['mis-sis-sip-pi', 'ta-ble'], 3, 2], 'gra-m-mar'), ('partial-repair probe', ['Categories', ['t1t', 'ca1t', '1p', '1m', 'r1r', '1ca', '.ta4', 'hen5at', 'a1b', '2io', 'ex1', 'gr2', '1na', 'con1', 'li1', '1q', 'ter1', '.un1', 'io3n.', 'hy3ph', 's1s', 'c2ce', '1tio'], ['pro-ject'], 3, 2], 'Categories'), ('regression: left hyphen minimum', ['Commitment', ['ex1', '.re1', 'io3n.', 'x1c', '1m', '1ble', 'con1', 'a2n', '3ty.', '1p', 'hen5at', 'p2h', 'an1d', 'hena4'], ['ex-cep-tion', 'ta-ble', 'pro-ject'], 3, 3], 'Com-mit-ment'), ('left minimum boundary', ['excellent', ['.ta4', 'a1b', 'b2l', '1ble', 'hy3ph', 'he2n', 'hena4', 'hen5at', '1na', 'n2at', '1tio', '2io', 'o2n', 'pu2', 'ter1', '1m', 'ex1', 'e1c', 'c2ce', 'con1', 'ment1', '4ing.', 'n1g', '.re1', 'gr2', '3ty.', 'li1', '1ca', 'ca1t', 'at1', 'io3n.', 'r1r', 'm1m', 'l1l', 't1t', 's1s', 'a2n', 'an1d', '5nd.', '1p', 'p2h', '1q', '.un1', 'e2x', 'x1c', '2mp', 'om1'], [], 2, 3], 'ex-cel-lent'), ('capitalised exception', ['Table', ['.ta4', 'a1b', 'b2l', '1ble', 'hy3ph', 'he2n', 'hena4', 'hen5at', '1na', 'n2at', '1tio', '2io', 'o2n', 'pu2', 'ter1', '1m', 'ex1', 'e1c', 'c2ce', 'con1', 'ment1', '4ing.', 'n1g', '.re1', 'gr2', '3ty.', 'li1', '1ca', 'ca1t', 'at1', 'io3n.', 'r1r', 'm1m', 'l1l', 't1t', 's1s', 'a2n', 'an1d', '5nd.', '1p', 'p2h', '1q', '.un1', 'e2x', 'x1c', '2mp', 'om1'], ['ta-ble'], 1, 1], 'Ta-ble'), ('control layout', ['Pentagon', ['1p', 'he2n', '.re1', 'at1', 'm1m', 'r1r', 'e1c', 'hena4', 'pu2', 'gr2', '1tio', 'ex1', 'n1g', '.ta4', 's1s', 'a2n', 'li1', 'n2at'], ['gram-mar', 'pro-ject'], 3, 1], 'Pentagon'), ('control layout', ['hyphenation', ['hy3ph', '1ble', '.re1', 'ter1', 'r1r', 'n1g', 'e2x', 'ca1t', 'pu2', 'om1', 'c2ce', '2mp', 'ex1', 'b2l'], ['ta-ble'], 1, 2], 'hy-phenation')], [('regression: left hyphen minimum', ['Commitment', ['at1', '1m', 'm1m', '4ing.', 'li1', 'he2n', 'e2x', 'e1c', 'l1l', '3ty.', 'ca1t', 'an1d', 'pu2', 'b2l', 's1s', '1na', 'a2n', 'ex1', '2mp', 'hena4', '1ble', 'om1', '1tio', '.re1', 'ter1', 'hen5at', 't1t', '2io', 'c2ce', 'r1r', 'gr2', 'n2at', 'p2h', 'x1c', 'a1b', 'ment1', 'con1', '.ta4', 'io3n.', '1ca', 'n1g', 'o2n', '5nd.', 'hy3ph', '.un1', '1q'], ['mis-sis-sip-pi'], 2, 1], 'Co-m-mit-ment'), ('regression: left hyphen minimum', ['Commitment', ['x1c', 'b2l', 'at1', 'a2n', 'ment1', 'o2n', 'n1g', 'hen5at', 'io3n.', 'e1c', 'e2x', 't1t', '.ta4', 'he2n', 'an1d', 'n2at', '1q', '1p', 'pu2', 'r1r', 'om1', '1ble', 'c2ce', '3ty.', 'con1', '2io', '1m', 'ter1', 'ca1t', '.re1', '2mp', 'p2h', '1na', '.un1', '5nd.', 'l1l', '4ing.', 'hena4', 'm1m', 's1s', 'ex1', 'li1'], [], 3, 2], 'Com-mit-ment'), ('partial-repair probe', ['hyphenation', ['gr2', '1tio', '1q', 'a2n', 'he2n', 'm1m', 'ment1', 'ca1t', 'an1d', '1p', 'io3n.', 'e1c', 'a1b', 'o2n', 'b2l', 'om1'], ['ex-cep-tion', 'mis-sis-sip-pi'], 3, 2], 'hyphena-tion'), ('partial-repair probe', ['category', ['o2n', '1q', '.ta4', 'r1r', 'x1c', 'pu2', 'n2at', '2mp', 'ment1', '1tio', '.re1', 'a2n', '.un1', 'ex1', 'p2h', 'hy3ph', 'b2l', 'c2ce', '1m', 'ca1t', 'm1m', 's1s', '3ty.', 'io3n.', 'a1b', '5nd.', '4ing.', 'l1l', '2io', 'an1d', 't1t', 'li1'], ['ex-cep-tion', 'gram-mar', 'pro-ject'], 3, 3], 'category'), ('right minimum boundary', ['category', ['.ta4', 'a1b', 'b2l', '1ble', 'hy3ph', 'he2n', 'hena4', 'hen5at', '1na', 'n2at', '1tio', '2io', 'o2n', 'pu2', 'ter1', '1m', 'ex1', 'e1c', 'c2ce', 'con1', 'ment1', '4ing.', 'n1g', '.re1', 'gr2', '3ty.', 'li1', '1ca', 'ca1t', 'at1', 'io3n.', 'r1r', 'm1m', 'l1l', 't1t', 's1s', 'a2n', 'an1d', '5nd.', '1p', 'p2h', '1q', '.un1', 'e2x', 'x1c', '2mp', 'om1'], [], 1, 3], 'ca-t-egory'), ('lowercase exception', ['project', ['.ta4', 'a1b', 'b2l', '1ble', 'hy3ph', 'he2n', 'hena4', 'hen5at', '1na', 'n2at', '1tio', '2io', 'o2n', 'pu2', 'ter1', '1m', 'ex1', 'e1c', 'c2ce', 'con1', 'ment1', '4ing.', 'n1g', '.re1', 'gr2', '3ty.', 'li1', '1ca', 'ca1t', 'at1', 'io3n.', 'r1r', 'm1m', 'l1l', 't1t', 's1s', 'a2n', 'an1d', '5nd.', '1p', 'p2h', '1q', '.un1', 'e2x', 'x1c', '2mp', 'om1'], ['pro-ject'], 2, 3], 'pro-ject'), ('control layout', ['table', ['s1s', 'ca1t', '1ca', '.re1', '2io', '1m', 'he2n', 'p2h', 'ment1', 'e1c', '1q', 'c2ce', 'o2n', 'r1r', 'l1l', 't1t', 'hen5at', 'om1', 'ter1', 'hy3ph', 'gr2', 'e2x', '5nd.', '.un1', '1p', 'b2l', 'a1b', 'x1c', 'n2at', '1ble', 'a2n', 'm1m', '1na', 'pu2', '3ty.', 'io3n.', 'ex1', 'con1', 'n1g', 'at1', 'hena4', 'an1d', '1tio', '.ta4', 'li1', '4ing.', '2mp'], ['mis-sis-sip-pi', 'pro-ject'], 1, 1], 'table'), ('control layout', ['announcement', ['1m', 'ex1', '1ca', '3ty.', '2mp', 'c2ce', 'ment1', '1na', 'hy3ph', 'he2n', 'con1', 'n1g', '1ble', 'om1', 'x1c', 'hen5at', 'e2x', 'n2at', 'm1m', 'ter1', '.re1', 'an1d', '1p', '2io', 'e1c', 'p2h', 'hena4', 'b2l', 'gr2', 'l1l'], ['ex-cep-tion'], 1, 2], 'announce-ment')], [('regression: left hyphen minimum', ['battle', ['.un1', 'ter1', 's1s', 'hena4', '3ty.', '1q', 'r1r', 'gr2', 'io3n.', 'om1', 'e1c', '2mp', '1ble', '.ta4', 'at1', 'ex1', 'a1b', 'a2n', 'e2x', 'he2n', 'pu2', 'o2n', '5nd.', 'hy3ph', 'li1', 'an1d', '2io'], [], 3, 1], 'bat-tle'), ('regression: left hyphen minimum', ['Categories', ['1m', 'ter1', '2io', '2mp', 'ex1', 'b2l', 'c2ce', 'gr2', 'li1', 'x1c', 'con1', 'o2n', 's1s', '.re1', 'ca1t'], ['gram-mar', 'pro-ject'], 2, 3], 'Ca-tegories'), ('partial-repair probe', ['Unexpected', ['1tio', 'l1l', 'li1', '1p', 'pu2', 'ter1', 'an1d', '2mp', '.un1', 'hy3ph', 'io3n.', 'a1b', '.re1', 'he2n', '1na', '2io', 't1t', '3ty.', 'ex1', '1m', 'n2at', 'ca1t', 'b2l', 'o2n', '.ta4', 'r1r', 'x1c', 'at1', 'con1', 'e2x', 'c2ce', '1ca', 'n1g', 'hena4', 's1s', 'm1m', 'e1c', '4ing.', '5nd.', 'gr2'], ['ta-ble'], 3, 1], 'Unex-pe-cted'), ('partial-repair probe', ['Categories', ['5nd.', 'he2n', 'hena4', '1q', 'an1d', '.ta4', 'li1', 'r1r', '1tio', 'x1c', 'om1', '.un1', 'ter1', 'n1g', '3ty.', 'gr2', 'con1', '1ca', 'c2ce', '4ing.', 'ment1', 'pu2', 'hen5at', 'a2n', 'ex1', 'm1m', 'io3n.', 't1t', 'ca1t', '1m', 'o2n'], ['pro-ject', 'gram-mar', 'ta-ble'], 3, 1], 'Categories'), ('word-final pattern ing.', ['running', ['.ta4', 'a1b', 'b2l', '1ble', 'hy3ph', 'he2n', 'hena4', 'hen5at', '1na', 'n2at', '1tio', '2io', 'o2n', 'pu2', 'ter1', '1m', 'ex1', 'e1c', 'c2ce', 'con1', 'ment1', '4ing.', 'n1g', '.re1', 'gr2', '3ty.', 'li1', '1ca', 'ca1t', 'at1', 'io3n.', 'r1r', 'm1m', 'l1l', 't1t', 's1s', 'a2n', 'an1d', '5nd.', '1p', 'p2h', '1q', '.un1', 'e2x', 'x1c', '2mp', 'om1'], [], 2, 2], 'running'), ('right minimum boundary', ['category', ['.ta4', 'a1b', 'b2l', '1ble', 'hy3ph', 'he2n', 'hena4', 'hen5at', '1na', 'n2at', '1tio', '2io', 'o2n', 'pu2', 'ter1', '1m', 'ex1', 'e1c', 'c2ce', 'con1', 'ment1', '4ing.', 'n1g', '.re1', 'gr2', '3ty.', 'li1', '1ca', 'ca1t', 'at1', 'io3n.', 'r1r', 'm1m', 'l1l', 't1t', 's1s', 'a2n', 'an1d', '5nd.', '1p', 'p2h', '1q', '.un1', 'e2x', 'x1c', '2mp', 'om1'], [], 1, 3], 'ca-t-egory'), ('control layout', ['understand', ['m1m', '4ing.', '1m', '1q', '1na', 't1t', 'ex1', '.re1'], ['ta-ble', 'mis-sis-sip-pi', 'ex-cep-tion'], 2, 2], 'understand'), ('control layout', ['literally', ['hena4', 'li1', '5nd.', 'om1', 'ex1', 'pu2', '1na', 'ca1t', 'hen5at', 'p2h', 'b2l', 'hy3ph', 's1s', 'ter1'], ['mis-sis-sip-pi'], 1, 3], 'li-ter-ally')]]
for label, args, expected in fixtures[N - 1]:
check(label, solve(args), expected)
print(json.dumps({"observations": observations, "passed": all(x["passed"] for x in observations)}, ensure_ascii=False))
raise SystemExit(0 if all(x["passed"] for x in observations) else 1)
| Boundary fixture | Actual | Expected | Outcome |
|---|---|---|---|
| left minimum boundary | excel-lent | ex-cel-lent | Failed |
| regression: left hyphen minimum | Commit-ment | Com-mit-ment | Failed |
| partial-repair probe | Categories | Categories | Passed |
| regression: left hyphen minimum | Commit-ment | Com-mit-ment | Failed |
| word-final pattern ing. | running | running | Passed |
| lowercase exception | pro-ject | pro-ject | Passed |
| control layout | Categories | Categories | Passed |
| control layout | Ta-ble | Ta-ble | Passed |
SHA-256 / 0a00aa9f832fab9fd37c7084ca476ff21a3b7bf6d551483a189ef50cae80938f
2 / The unsuccessful fix
Exit 1"""Failure Map reference implementation. Python standard library only."""
import json
N = 1
observations = []
def solve(x):
word, patterns, exceptions, lmin, rmin = x
low = word.lower()
for e in exceptions:
if e.replace('-', '') == low:
out, count = '', 0
for c in e:
if c == '-':
out += '-'
else:
out += word[count]
count += 1
return out
table = {}
for p in patterns:
letters = ''
vals = [0]
for c in p:
if c.isdigit():
vals[-1] = int(c)
else:
letters += c
vals.append(0)
table[letters] = vals
dotted = '.' + low + '.'
score = [0] * (len(dotted) + 1)
for s in range(len(dotted)):
for e in range(s + 1, len(dotted) + 1):
vals = table.get(dotted[s:e])
if vals:
for k, v in enumerate(vals):
score[s + k] = max(score[s + k], v)
points = [i for i in range(1, len(word)) if score[i + 1] % 2 == 1 and i >= lmin - 1 and len(word) - i >= rmin]
out = ''
for i, c in enumerate(word):
if i in points:
out += '-'
out += c
return out
def check(label, actual, expected):
observations.append({"check": label, "actual": actual, "expected": expected, "passed": actual == expected})
fixtures = [[('left minimum boundary', ['excellent', ['.ta4', 'a1b', 'b2l', '1ble', 'hy3ph', 'he2n', 'hena4', 'hen5at', '1na', 'n2at', '1tio', '2io', 'o2n', 'pu2', 'ter1', '1m', 'ex1', 'e1c', 'c2ce', 'con1', 'ment1', '4ing.', 'n1g', '.re1', 'gr2', '3ty.', 'li1', '1ca', 'ca1t', 'at1', 'io3n.', 'r1r', 'm1m', 'l1l', 't1t', 's1s', 'a2n', 'an1d', '5nd.', '1p', 'p2h', '1q', '.un1', 'e2x', 'x1c', '2mp', 'om1'], [], 2, 3], 'ex-cel-lent'), ('regression: left hyphen minimum', ['Commitment', ['io3n.', 'hen5at', '3ty.', '1p', 'ca1t', '.ta4', 'x1c', 'n2at', 'm1m', 'e1c', 'r1r', 'hy3ph', 'ter1', '.un1', 's1s', 'hena4', '2mp', 'p2h', 'o2n', 'at1', '1q', 'he2n', '1m', 'ment1', '1ca', 'l1l', '.re1', '2io', '5nd.', 'c2ce', 'an1d', 'li1', 'b2l', 'a2n', 'om1', 'n1g', '1ble', 'pu2', 't1t', 'ex1', '1na', '4ing.'], [], 3, 2], 'Com-mit-ment'), ('partial-repair probe', ['Categories', ['1ca', '.re1', '.un1', '2io', 'a1b', 'con1', 'p2h', 'li1', 'o2n', 'n1g', '3ty.', 'ca1t'], ['ex-cep-tion', 'pro-ject'], 3, 2], 'Categories'), ('regression: left hyphen minimum', ['Commitment', ['ex1', '.re1', 'io3n.', 'x1c', '1m', '1ble', 'con1', 'a2n', '3ty.', '1p', 'hen5at', 'p2h', 'an1d', 'hena4'], ['ex-cep-tion', 'ta-ble', 'pro-ject'], 3, 3], 'Com-mit-ment'), ('word-final pattern ing.', ['running', ['.ta4', 'a1b', 'b2l', '1ble', 'hy3ph', 'he2n', 'hena4', 'hen5at', '1na', 'n2at', '1tio', '2io', 'o2n', 'pu2', 'ter1', '1m', 'ex1', 'e1c', 'c2ce', 'con1', 'ment1', '4ing.', 'n1g', '.re1', 'gr2', '3ty.', 'li1', '1ca', 'ca1t', 'at1', 'io3n.', 'r1r', 'm1m', 'l1l', 't1t', 's1s', 'a2n', 'an1d', '5nd.', '1p', 'p2h', '1q', '.un1', 'e2x', 'x1c', '2mp', 'om1'], [], 2, 2], 'running'), ('lowercase exception', ['project', ['.ta4', 'a1b', 'b2l', '1ble', 'hy3ph', 'he2n', 'hena4', 'hen5at', '1na', 'n2at', '1tio', '2io', 'o2n', 'pu2', 'ter1', '1m', 'ex1', 'e1c', 'c2ce', 'con1', 'ment1', '4ing.', 'n1g', '.re1', 'gr2', '3ty.', 'li1', '1ca', 'ca1t', 'at1', 'io3n.', 'r1r', 'm1m', 'l1l', 't1t', 's1s', 'a2n', 'an1d', '5nd.', '1p', 'p2h', '1q', '.un1', 'e2x', 'x1c', '2mp', 'om1'], ['pro-ject'], 2, 3], 'pro-ject'), ('control layout', ['Categories', ['.ta4', 'c2ce', 's1s', 'x1c', 'p2h', '1p', 'pu2', 'o2n', 'r1r', 'io3n.', 'ment1', 'an1d', '3ty.', 'n1g', '.re1', '2mp', 'a1b', '1ca', 'li1'], ['ta-ble', 'gram-mar', 'pro-ject'], 2, 1], 'Categories'), ('control layout', ['Table', ['ex1', 'hy3ph', 'pu2', '.ta4', '4ing.', '1q', 'n2at', '1tio', '.re1', 'b2l', '2io', 'a1b'], ['ta-ble', 'mis-sis-sip-pi', 'pro-ject'], 2, 2], 'Ta-ble')], [('regression: left hyphen minimum', ['typesetting', ['ca1t', '.ta4', 'e1c', 'ment1', '1p', '1ble', 'p2h', 'n2at', 'a2n', '1tio', 'x1c', 'gr2', '2io', 'e2x', 'm1m', 'r1r', 'a1b', 'con1', 'io3n.', '.re1', 'l1l', '1ca', 'om1', 'hena4', '2mp', 't1t', 'li1'], ['gram-mar', 'pro-ject'], 2, 2], 'ty-peset-ting'), ('regression: left hyphen minimum', ['hyphenation', ['hy3ph', 'r1r', 'ment1', '.re1', 'li1', '1ble', 'hen5at', 't1t', '1m', 'c2ce', 'm1m'], [], 2, 2], 'hy-phen-ation'), ('partial-repair probe', ['understand', ['ca1t', 'l1l', 'an1d', 'n2at', 'a2n', 'gr2', 'c2ce', '3ty.', '1m', 'r1r', '1na', '2mp', 'he2n', '4ing.', 'ter1', 'a1b', 'om1', 'e1c', 'hen5at', 'n1g', '1ca', 'm1m', '2io', 'b2l', '.un1', 'pu2', 'hena4', 'o2n', '1p'], ['mis-sis-sip-pi', 'ta-ble'], 3, 2], 'understand'), ('partial-repair probe', ['Categories', ['t1t', 'ca1t', '1p', '1m', 'r1r', '1ca', '.ta4', 'hen5at', 'a1b', '2io', 'ex1', 'gr2', '1na', 'con1', 'li1', '1q', 'ter1', '.un1', 'io3n.', 'hy3ph', 's1s', 'c2ce', '1tio'], ['pro-ject'], 3, 2], 'Categories'), ('word-final pattern ing.', ['running', ['.ta4', 'a1b', 'b2l', '1ble', 'hy3ph', 'he2n', 'hena4', 'hen5at', '1na', 'n2at', '1tio', '2io', 'o2n', 'pu2', 'ter1', '1m', 'ex1', 'e1c', 'c2ce', 'con1', 'ment1', '4ing.', 'n1g', '.re1', 'gr2', '3ty.', 'li1', '1ca', 'ca1t', 'at1', 'io3n.', 'r1r', 'm1m', 'l1l', 't1t', 's1s', 'a2n', 'an1d', '5nd.', '1p', 'p2h', '1q', '.un1', 'e2x', 'x1c', '2mp', 'om1'], [], 2, 2], 'running'), ('left minimum boundary', ['excellent', ['.ta4', 'a1b', 'b2l', '1ble', 'hy3ph', 'he2n', 'hena4', 'hen5at', '1na', 'n2at', '1tio', '2io', 'o2n', 'pu2', 'ter1', '1m', 'ex1', 'e1c', 'c2ce', 'con1', 'ment1', '4ing.', 'n1g', '.re1', 'gr2', '3ty.', 'li1', '1ca', 'ca1t', 'at1', 'io3n.', 'r1r', 'm1m', 'l1l', 't1t', 's1s', 'a2n', 'an1d', '5nd.', '1p', 'p2h', '1q', '.un1', 'e2x', 'x1c', '2mp', 'om1'], [], 2, 3], 'ex-cel-lent'), ('control layout', ['table', ['c2ce', '3ty.', 'he2n', '2io', 's1s', '.un1', 'con1', 'hena4', '1p', 'ca1t', 'n2at', '4ing.', 'om1', 'ment1', 'a1b', 'a2n', 'gr2', 'p2h', '1tio', 'li1', 'ex1', '1ca', '1m', 'ter1'], ['ex-cep-tion'], 1, 1], 'ta-ble'), ('control layout', ['Exception', ['he2n', '.re1', '3ty.', 'e2x', 'n2at', 'e1c', '2mp', '1m', '.ta4', '2io', 'a1b', 'hen5at', '1ble', 'ex1', 'at1', 'an1d', 'ca1t', 'io3n.'], ['gram-mar', 'mis-sis-sip-pi'], 1, 2], 'Ex-ception')], [('regression: left hyphen minimum', ['typesetting', ['ex1', 'b2l', '1ble', 'hena4', 'pu2', 'e2x', '.un1', 'a1b', 'r1r', '5nd.', 'con1', 'io3n.', 'c2ce', '1q', 'n2at', 'ter1', 'l1l', '1na', 'o2n', 'hen5at', 'x1c', 's1s', '2io', 'an1d', 'a2n', 'hy3ph', '3ty.', 'n1g', 'at1', '1p', 'gr2', '4ing.', 't1t', '2mp', 'li1', 'ca1t', '1m', 'he2n', 'p2h', '1ca', 'ment1', '1tio', 'm1m', '.re1', 'om1', 'e1c', '.ta4'], [], 2, 3], 'ty-peset-ting'), ('regression: left hyphen minimum', ['grammar', ['c2ce', '5nd.', '1tio', '1m', 'a2n', '1q', 'gr2', 's1s', 'l1l', 'n2at', 'o2n', 'hy3ph', 'n1g', '1na', 'con1', 'e2x', '4ing.', 'at1', 't1t', 'pu2', '.re1', '2mp', 'ment1', 'e1c', 'r1r', '1ca', 'io3n.', 'ex1', 'li1', '.un1', 'x1c', 'a1b', 'p2h'], ['mis-sis-sip-pi', 'ta-ble'], 3, 2], 'gra-m-mar'), ('partial-repair probe', ['Categories', ['t1t', 'ca1t', '1p', '1m', 'r1r', '1ca', '.ta4', 'hen5at', 'a1b', '2io', 'ex1', 'gr2', '1na', 'con1', 'li1', '1q', 'ter1', '.un1', 'io3n.', 'hy3ph', 's1s', 'c2ce', '1tio'], ['pro-ject'], 3, 2], 'Categories'), ('regression: left hyphen minimum', ['Commitment', ['ex1', '.re1', 'io3n.', 'x1c', '1m', '1ble', 'con1', 'a2n', '3ty.', '1p', 'hen5at', 'p2h', 'an1d', 'hena4'], ['ex-cep-tion', 'ta-ble', 'pro-ject'], 3, 3], 'Com-mit-ment'), ('left minimum boundary', ['excellent', ['.ta4', 'a1b', 'b2l', '1ble', 'hy3ph', 'he2n', 'hena4', 'hen5at', '1na', 'n2at', '1tio', '2io', 'o2n', 'pu2', 'ter1', '1m', 'ex1', 'e1c', 'c2ce', 'con1', 'ment1', '4ing.', 'n1g', '.re1', 'gr2', '3ty.', 'li1', '1ca', 'ca1t', 'at1', 'io3n.', 'r1r', 'm1m', 'l1l', 't1t', 's1s', 'a2n', 'an1d', '5nd.', '1p', 'p2h', '1q', '.un1', 'e2x', 'x1c', '2mp', 'om1'], [], 2, 3], 'ex-cel-lent'), ('capitalised exception', ['Table', ['.ta4', 'a1b', 'b2l', '1ble', 'hy3ph', 'he2n', 'hena4', 'hen5at', '1na', 'n2at', '1tio', '2io', 'o2n', 'pu2', 'ter1', '1m', 'ex1', 'e1c', 'c2ce', 'con1', 'ment1', '4ing.', 'n1g', '.re1', 'gr2', '3ty.', 'li1', '1ca', 'ca1t', 'at1', 'io3n.', 'r1r', 'm1m', 'l1l', 't1t', 's1s', 'a2n', 'an1d', '5nd.', '1p', 'p2h', '1q', '.un1', 'e2x', 'x1c', '2mp', 'om1'], ['ta-ble'], 1, 1], 'Ta-ble'), ('control layout', ['Pentagon', ['1p', 'he2n', '.re1', 'at1', 'm1m', 'r1r', 'e1c', 'hena4', 'pu2', 'gr2', '1tio', 'ex1', 'n1g', '.ta4', 's1s', 'a2n', 'li1', 'n2at'], ['gram-mar', 'pro-ject'], 3, 1], 'Pentagon'), ('control layout', ['hyphenation', ['hy3ph', '1ble', '.re1', 'ter1', 'r1r', 'n1g', 'e2x', 'ca1t', 'pu2', 'om1', 'c2ce', '2mp', 'ex1', 'b2l'], ['ta-ble'], 1, 2], 'hy-phenation')], [('regression: left hyphen minimum', ['Commitment', ['at1', '1m', 'm1m', '4ing.', 'li1', 'he2n', 'e2x', 'e1c', 'l1l', '3ty.', 'ca1t', 'an1d', 'pu2', 'b2l', 's1s', '1na', 'a2n', 'ex1', '2mp', 'hena4', '1ble', 'om1', '1tio', '.re1', 'ter1', 'hen5at', 't1t', '2io', 'c2ce', 'r1r', 'gr2', 'n2at', 'p2h', 'x1c', 'a1b', 'ment1', 'con1', '.ta4', 'io3n.', '1ca', 'n1g', 'o2n', '5nd.', 'hy3ph', '.un1', '1q'], ['mis-sis-sip-pi'], 2, 1], 'Co-m-mit-ment'), ('regression: left hyphen minimum', ['Commitment', ['x1c', 'b2l', 'at1', 'a2n', 'ment1', 'o2n', 'n1g', 'hen5at', 'io3n.', 'e1c', 'e2x', 't1t', '.ta4', 'he2n', 'an1d', 'n2at', '1q', '1p', 'pu2', 'r1r', 'om1', '1ble', 'c2ce', '3ty.', 'con1', '2io', '1m', 'ter1', 'ca1t', '.re1', '2mp', 'p2h', '1na', '.un1', '5nd.', 'l1l', '4ing.', 'hena4', 'm1m', 's1s', 'ex1', 'li1'], [], 3, 2], 'Com-mit-ment'), ('partial-repair probe', ['hyphenation', ['gr2', '1tio', '1q', 'a2n', 'he2n', 'm1m', 'ment1', 'ca1t', 'an1d', '1p', 'io3n.', 'e1c', 'a1b', 'o2n', 'b2l', 'om1'], ['ex-cep-tion', 'mis-sis-sip-pi'], 3, 2], 'hyphena-tion'), ('partial-repair probe', ['category', ['o2n', '1q', '.ta4', 'r1r', 'x1c', 'pu2', 'n2at', '2mp', 'ment1', '1tio', '.re1', 'a2n', '.un1', 'ex1', 'p2h', 'hy3ph', 'b2l', 'c2ce', '1m', 'ca1t', 'm1m', 's1s', '3ty.', 'io3n.', 'a1b', '5nd.', '4ing.', 'l1l', '2io', 'an1d', 't1t', 'li1'], ['ex-cep-tion', 'gram-mar', 'pro-ject'], 3, 3], 'category'), ('right minimum boundary', ['category', ['.ta4', 'a1b', 'b2l', '1ble', 'hy3ph', 'he2n', 'hena4', 'hen5at', '1na', 'n2at', '1tio', '2io', 'o2n', 'pu2', 'ter1', '1m', 'ex1', 'e1c', 'c2ce', 'con1', 'ment1', '4ing.', 'n1g', '.re1', 'gr2', '3ty.', 'li1', '1ca', 'ca1t', 'at1', 'io3n.', 'r1r', 'm1m', 'l1l', 't1t', 's1s', 'a2n', 'an1d', '5nd.', '1p', 'p2h', '1q', '.un1', 'e2x', 'x1c', '2mp', 'om1'], [], 1, 3], 'ca-t-egory'), ('lowercase exception', ['project', ['.ta4', 'a1b', 'b2l', '1ble', 'hy3ph', 'he2n', 'hena4', 'hen5at', '1na', 'n2at', '1tio', '2io', 'o2n', 'pu2', 'ter1', '1m', 'ex1', 'e1c', 'c2ce', 'con1', 'ment1', '4ing.', 'n1g', '.re1', 'gr2', '3ty.', 'li1', '1ca', 'ca1t', 'at1', 'io3n.', 'r1r', 'm1m', 'l1l', 't1t', 's1s', 'a2n', 'an1d', '5nd.', '1p', 'p2h', '1q', '.un1', 'e2x', 'x1c', '2mp', 'om1'], ['pro-ject'], 2, 3], 'pro-ject'), ('control layout', ['table', ['s1s', 'ca1t', '1ca', '.re1', '2io', '1m', 'he2n', 'p2h', 'ment1', 'e1c', '1q', 'c2ce', 'o2n', 'r1r', 'l1l', 't1t', 'hen5at', 'om1', 'ter1', 'hy3ph', 'gr2', 'e2x', '5nd.', '.un1', '1p', 'b2l', 'a1b', 'x1c', 'n2at', '1ble', 'a2n', 'm1m', '1na', 'pu2', '3ty.', 'io3n.', 'ex1', 'con1', 'n1g', 'at1', 'hena4', 'an1d', '1tio', '.ta4', 'li1', '4ing.', '2mp'], ['mis-sis-sip-pi', 'pro-ject'], 1, 1], 'table'), ('control layout', ['announcement', ['1m', 'ex1', '1ca', '3ty.', '2mp', 'c2ce', 'ment1', '1na', 'hy3ph', 'he2n', 'con1', 'n1g', '1ble', 'om1', 'x1c', 'hen5at', 'e2x', 'n2at', 'm1m', 'ter1', '.re1', 'an1d', '1p', '2io', 'e1c', 'p2h', 'hena4', 'b2l', 'gr2', 'l1l'], ['ex-cep-tion'], 1, 2], 'announce-ment')], [('regression: left hyphen minimum', ['battle', ['.un1', 'ter1', 's1s', 'hena4', '3ty.', '1q', 'r1r', 'gr2', 'io3n.', 'om1', 'e1c', '2mp', '1ble', '.ta4', 'at1', 'ex1', 'a1b', 'a2n', 'e2x', 'he2n', 'pu2', 'o2n', '5nd.', 'hy3ph', 'li1', 'an1d', '2io'], [], 3, 1], 'bat-tle'), ('regression: left hyphen minimum', ['Categories', ['1m', 'ter1', '2io', '2mp', 'ex1', 'b2l', 'c2ce', 'gr2', 'li1', 'x1c', 'con1', 'o2n', 's1s', '.re1', 'ca1t'], ['gram-mar', 'pro-ject'], 2, 3], 'Ca-tegories'), ('partial-repair probe', ['Unexpected', ['1tio', 'l1l', 'li1', '1p', 'pu2', 'ter1', 'an1d', '2mp', '.un1', 'hy3ph', 'io3n.', 'a1b', '.re1', 'he2n', '1na', '2io', 't1t', '3ty.', 'ex1', '1m', 'n2at', 'ca1t', 'b2l', 'o2n', '.ta4', 'r1r', 'x1c', 'at1', 'con1', 'e2x', 'c2ce', '1ca', 'n1g', 'hena4', 's1s', 'm1m', 'e1c', '4ing.', '5nd.', 'gr2'], ['ta-ble'], 3, 1], 'Unex-pe-cted'), ('partial-repair probe', ['Categories', ['5nd.', 'he2n', 'hena4', '1q', 'an1d', '.ta4', 'li1', 'r1r', '1tio', 'x1c', 'om1', '.un1', 'ter1', 'n1g', '3ty.', 'gr2', 'con1', '1ca', 'c2ce', '4ing.', 'ment1', 'pu2', 'hen5at', 'a2n', 'ex1', 'm1m', 'io3n.', 't1t', 'ca1t', '1m', 'o2n'], ['pro-ject', 'gram-mar', 'ta-ble'], 3, 1], 'Categories'), ('word-final pattern ing.', ['running', ['.ta4', 'a1b', 'b2l', '1ble', 'hy3ph', 'he2n', 'hena4', 'hen5at', '1na', 'n2at', '1tio', '2io', 'o2n', 'pu2', 'ter1', '1m', 'ex1', 'e1c', 'c2ce', 'con1', 'ment1', '4ing.', 'n1g', '.re1', 'gr2', '3ty.', 'li1', '1ca', 'ca1t', 'at1', 'io3n.', 'r1r', 'm1m', 'l1l', 't1t', 's1s', 'a2n', 'an1d', '5nd.', '1p', 'p2h', '1q', '.un1', 'e2x', 'x1c', '2mp', 'om1'], [], 2, 2], 'running'), ('right minimum boundary', ['category', ['.ta4', 'a1b', 'b2l', '1ble', 'hy3ph', 'he2n', 'hena4', 'hen5at', '1na', 'n2at', '1tio', '2io', 'o2n', 'pu2', 'ter1', '1m', 'ex1', 'e1c', 'c2ce', 'con1', 'ment1', '4ing.', 'n1g', '.re1', 'gr2', '3ty.', 'li1', '1ca', 'ca1t', 'at1', 'io3n.', 'r1r', 'm1m', 'l1l', 't1t', 's1s', 'a2n', 'an1d', '5nd.', '1p', 'p2h', '1q', '.un1', 'e2x', 'x1c', '2mp', 'om1'], [], 1, 3], 'ca-t-egory'), ('control layout', ['understand', ['m1m', '4ing.', '1m', '1q', '1na', 't1t', 'ex1', '.re1'], ['ta-ble', 'mis-sis-sip-pi', 'ex-cep-tion'], 2, 2], 'understand'), ('control layout', ['literally', ['hena4', 'li1', '5nd.', 'om1', 'ex1', 'pu2', '1na', 'ca1t', 'hen5at', 'p2h', 'b2l', 'hy3ph', 's1s', 'ter1'], ['mis-sis-sip-pi'], 1, 3], 'li-ter-ally')]]
for label, args, expected in fixtures[N - 1]:
check(label, solve(args), expected)
print(json.dumps({"observations": observations, "passed": all(x["passed"] for x in observations)}, ensure_ascii=False))
raise SystemExit(0 if all(x["passed"] for x in observations) else 1)
| Boundary fixture | Actual | Expected | Outcome |
|---|---|---|---|
| left minimum boundary | ex-cel-lent | ex-cel-lent | Passed |
| regression: left hyphen minimum | Co-m-mit-ment | Com-mit-ment | Failed |
| partial-repair probe | Ca-tegories | Categories | Failed |
| regression: left hyphen minimum | Co-m-mit-ment | Com-mit-ment | Failed |
| word-final pattern ing. | running | running | Passed |
| lowercase exception | pro-ject | pro-ject | Passed |
| control layout | Categories | Categories | Passed |
| control layout | Ta-ble | Ta-ble | Passed |
SHA-256 / 3efea1529364b9f33d1e0a1b6a34ca6036fc3ab21c5d805dafc69a2463ec0a57
3 / The verified repair
Exit 0"""Failure Map reference implementation. Python standard library only."""
import json
N = 1
observations = []
def solve(x):
word, patterns, exceptions, lmin, rmin = x
low = word.lower()
for e in exceptions:
if e.replace('-', '') == low:
out, count = '', 0
for c in e:
if c == '-':
out += '-'
else:
out += word[count]
count += 1
return out
table = {}
for p in patterns:
letters = ''
vals = [0]
for c in p:
if c.isdigit():
vals[-1] = int(c)
else:
letters += c
vals.append(0)
table[letters] = vals
dotted = '.' + low + '.'
score = [0] * (len(dotted) + 1)
for s in range(len(dotted)):
for e in range(s + 1, len(dotted) + 1):
vals = table.get(dotted[s:e])
if vals:
for k, v in enumerate(vals):
score[s + k] = max(score[s + k], v)
points = [i for i in range(1, len(word)) if score[i + 1] % 2 == 1 and i >= lmin and len(word) - i >= rmin]
out = ''
for i, c in enumerate(word):
if i in points:
out += '-'
out += c
return out
def check(label, actual, expected):
observations.append({"check": label, "actual": actual, "expected": expected, "passed": actual == expected})
fixtures = [[('left minimum boundary', ['excellent', ['.ta4', 'a1b', 'b2l', '1ble', 'hy3ph', 'he2n', 'hena4', 'hen5at', '1na', 'n2at', '1tio', '2io', 'o2n', 'pu2', 'ter1', '1m', 'ex1', 'e1c', 'c2ce', 'con1', 'ment1', '4ing.', 'n1g', '.re1', 'gr2', '3ty.', 'li1', '1ca', 'ca1t', 'at1', 'io3n.', 'r1r', 'm1m', 'l1l', 't1t', 's1s', 'a2n', 'an1d', '5nd.', '1p', 'p2h', '1q', '.un1', 'e2x', 'x1c', '2mp', 'om1'], [], 2, 3], 'ex-cel-lent'), ('regression: left hyphen minimum', ['Commitment', ['io3n.', 'hen5at', '3ty.', '1p', 'ca1t', '.ta4', 'x1c', 'n2at', 'm1m', 'e1c', 'r1r', 'hy3ph', 'ter1', '.un1', 's1s', 'hena4', '2mp', 'p2h', 'o2n', 'at1', '1q', 'he2n', '1m', 'ment1', '1ca', 'l1l', '.re1', '2io', '5nd.', 'c2ce', 'an1d', 'li1', 'b2l', 'a2n', 'om1', 'n1g', '1ble', 'pu2', 't1t', 'ex1', '1na', '4ing.'], [], 3, 2], 'Com-mit-ment'), ('partial-repair probe', ['Categories', ['1ca', '.re1', '.un1', '2io', 'a1b', 'con1', 'p2h', 'li1', 'o2n', 'n1g', '3ty.', 'ca1t'], ['ex-cep-tion', 'pro-ject'], 3, 2], 'Categories'), ('regression: left hyphen minimum', ['Commitment', ['ex1', '.re1', 'io3n.', 'x1c', '1m', '1ble', 'con1', 'a2n', '3ty.', '1p', 'hen5at', 'p2h', 'an1d', 'hena4'], ['ex-cep-tion', 'ta-ble', 'pro-ject'], 3, 3], 'Com-mit-ment'), ('word-final pattern ing.', ['running', ['.ta4', 'a1b', 'b2l', '1ble', 'hy3ph', 'he2n', 'hena4', 'hen5at', '1na', 'n2at', '1tio', '2io', 'o2n', 'pu2', 'ter1', '1m', 'ex1', 'e1c', 'c2ce', 'con1', 'ment1', '4ing.', 'n1g', '.re1', 'gr2', '3ty.', 'li1', '1ca', 'ca1t', 'at1', 'io3n.', 'r1r', 'm1m', 'l1l', 't1t', 's1s', 'a2n', 'an1d', '5nd.', '1p', 'p2h', '1q', '.un1', 'e2x', 'x1c', '2mp', 'om1'], [], 2, 2], 'running'), ('lowercase exception', ['project', ['.ta4', 'a1b', 'b2l', '1ble', 'hy3ph', 'he2n', 'hena4', 'hen5at', '1na', 'n2at', '1tio', '2io', 'o2n', 'pu2', 'ter1', '1m', 'ex1', 'e1c', 'c2ce', 'con1', 'ment1', '4ing.', 'n1g', '.re1', 'gr2', '3ty.', 'li1', '1ca', 'ca1t', 'at1', 'io3n.', 'r1r', 'm1m', 'l1l', 't1t', 's1s', 'a2n', 'an1d', '5nd.', '1p', 'p2h', '1q', '.un1', 'e2x', 'x1c', '2mp', 'om1'], ['pro-ject'], 2, 3], 'pro-ject'), ('control layout', ['Categories', ['.ta4', 'c2ce', 's1s', 'x1c', 'p2h', '1p', 'pu2', 'o2n', 'r1r', 'io3n.', 'ment1', 'an1d', '3ty.', 'n1g', '.re1', '2mp', 'a1b', '1ca', 'li1'], ['ta-ble', 'gram-mar', 'pro-ject'], 2, 1], 'Categories'), ('control layout', ['Table', ['ex1', 'hy3ph', 'pu2', '.ta4', '4ing.', '1q', 'n2at', '1tio', '.re1', 'b2l', '2io', 'a1b'], ['ta-ble', 'mis-sis-sip-pi', 'pro-ject'], 2, 2], 'Ta-ble')], [('regression: left hyphen minimum', ['typesetting', ['ca1t', '.ta4', 'e1c', 'ment1', '1p', '1ble', 'p2h', 'n2at', 'a2n', '1tio', 'x1c', 'gr2', '2io', 'e2x', 'm1m', 'r1r', 'a1b', 'con1', 'io3n.', '.re1', 'l1l', '1ca', 'om1', 'hena4', '2mp', 't1t', 'li1'], ['gram-mar', 'pro-ject'], 2, 2], 'ty-peset-ting'), ('regression: left hyphen minimum', ['hyphenation', ['hy3ph', 'r1r', 'ment1', '.re1', 'li1', '1ble', 'hen5at', 't1t', '1m', 'c2ce', 'm1m'], [], 2, 2], 'hy-phen-ation'), ('partial-repair probe', ['understand', ['ca1t', 'l1l', 'an1d', 'n2at', 'a2n', 'gr2', 'c2ce', '3ty.', '1m', 'r1r', '1na', '2mp', 'he2n', '4ing.', 'ter1', 'a1b', 'om1', 'e1c', 'hen5at', 'n1g', '1ca', 'm1m', '2io', 'b2l', '.un1', 'pu2', 'hena4', 'o2n', '1p'], ['mis-sis-sip-pi', 'ta-ble'], 3, 2], 'understand'), ('partial-repair probe', ['Categories', ['t1t', 'ca1t', '1p', '1m', 'r1r', '1ca', '.ta4', 'hen5at', 'a1b', '2io', 'ex1', 'gr2', '1na', 'con1', 'li1', '1q', 'ter1', '.un1', 'io3n.', 'hy3ph', 's1s', 'c2ce', '1tio'], ['pro-ject'], 3, 2], 'Categories'), ('word-final pattern ing.', ['running', ['.ta4', 'a1b', 'b2l', '1ble', 'hy3ph', 'he2n', 'hena4', 'hen5at', '1na', 'n2at', '1tio', '2io', 'o2n', 'pu2', 'ter1', '1m', 'ex1', 'e1c', 'c2ce', 'con1', 'ment1', '4ing.', 'n1g', '.re1', 'gr2', '3ty.', 'li1', '1ca', 'ca1t', 'at1', 'io3n.', 'r1r', 'm1m', 'l1l', 't1t', 's1s', 'a2n', 'an1d', '5nd.', '1p', 'p2h', '1q', '.un1', 'e2x', 'x1c', '2mp', 'om1'], [], 2, 2], 'running'), ('left minimum boundary', ['excellent', ['.ta4', 'a1b', 'b2l', '1ble', 'hy3ph', 'he2n', 'hena4', 'hen5at', '1na', 'n2at', '1tio', '2io', 'o2n', 'pu2', 'ter1', '1m', 'ex1', 'e1c', 'c2ce', 'con1', 'ment1', '4ing.', 'n1g', '.re1', 'gr2', '3ty.', 'li1', '1ca', 'ca1t', 'at1', 'io3n.', 'r1r', 'm1m', 'l1l', 't1t', 's1s', 'a2n', 'an1d', '5nd.', '1p', 'p2h', '1q', '.un1', 'e2x', 'x1c', '2mp', 'om1'], [], 2, 3], 'ex-cel-lent'), ('control layout', ['table', ['c2ce', '3ty.', 'he2n', '2io', 's1s', '.un1', 'con1', 'hena4', '1p', 'ca1t', 'n2at', '4ing.', 'om1', 'ment1', 'a1b', 'a2n', 'gr2', 'p2h', '1tio', 'li1', 'ex1', '1ca', '1m', 'ter1'], ['ex-cep-tion'], 1, 1], 'ta-ble'), ('control layout', ['Exception', ['he2n', '.re1', '3ty.', 'e2x', 'n2at', 'e1c', '2mp', '1m', '.ta4', '2io', 'a1b', 'hen5at', '1ble', 'ex1', 'at1', 'an1d', 'ca1t', 'io3n.'], ['gram-mar', 'mis-sis-sip-pi'], 1, 2], 'Ex-ception')], [('regression: left hyphen minimum', ['typesetting', ['ex1', 'b2l', '1ble', 'hena4', 'pu2', 'e2x', '.un1', 'a1b', 'r1r', '5nd.', 'con1', 'io3n.', 'c2ce', '1q', 'n2at', 'ter1', 'l1l', '1na', 'o2n', 'hen5at', 'x1c', 's1s', '2io', 'an1d', 'a2n', 'hy3ph', '3ty.', 'n1g', 'at1', '1p', 'gr2', '4ing.', 't1t', '2mp', 'li1', 'ca1t', '1m', 'he2n', 'p2h', '1ca', 'ment1', '1tio', 'm1m', '.re1', 'om1', 'e1c', '.ta4'], [], 2, 3], 'ty-peset-ting'), ('regression: left hyphen minimum', ['grammar', ['c2ce', '5nd.', '1tio', '1m', 'a2n', '1q', 'gr2', 's1s', 'l1l', 'n2at', 'o2n', 'hy3ph', 'n1g', '1na', 'con1', 'e2x', '4ing.', 'at1', 't1t', 'pu2', '.re1', '2mp', 'ment1', 'e1c', 'r1r', '1ca', 'io3n.', 'ex1', 'li1', '.un1', 'x1c', 'a1b', 'p2h'], ['mis-sis-sip-pi', 'ta-ble'], 3, 2], 'gra-m-mar'), ('partial-repair probe', ['Categories', ['t1t', 'ca1t', '1p', '1m', 'r1r', '1ca', '.ta4', 'hen5at', 'a1b', '2io', 'ex1', 'gr2', '1na', 'con1', 'li1', '1q', 'ter1', '.un1', 'io3n.', 'hy3ph', 's1s', 'c2ce', '1tio'], ['pro-ject'], 3, 2], 'Categories'), ('regression: left hyphen minimum', ['Commitment', ['ex1', '.re1', 'io3n.', 'x1c', '1m', '1ble', 'con1', 'a2n', '3ty.', '1p', 'hen5at', 'p2h', 'an1d', 'hena4'], ['ex-cep-tion', 'ta-ble', 'pro-ject'], 3, 3], 'Com-mit-ment'), ('left minimum boundary', ['excellent', ['.ta4', 'a1b', 'b2l', '1ble', 'hy3ph', 'he2n', 'hena4', 'hen5at', '1na', 'n2at', '1tio', '2io', 'o2n', 'pu2', 'ter1', '1m', 'ex1', 'e1c', 'c2ce', 'con1', 'ment1', '4ing.', 'n1g', '.re1', 'gr2', '3ty.', 'li1', '1ca', 'ca1t', 'at1', 'io3n.', 'r1r', 'm1m', 'l1l', 't1t', 's1s', 'a2n', 'an1d', '5nd.', '1p', 'p2h', '1q', '.un1', 'e2x', 'x1c', '2mp', 'om1'], [], 2, 3], 'ex-cel-lent'), ('capitalised exception', ['Table', ['.ta4', 'a1b', 'b2l', '1ble', 'hy3ph', 'he2n', 'hena4', 'hen5at', '1na', 'n2at', '1tio', '2io', 'o2n', 'pu2', 'ter1', '1m', 'ex1', 'e1c', 'c2ce', 'con1', 'ment1', '4ing.', 'n1g', '.re1', 'gr2', '3ty.', 'li1', '1ca', 'ca1t', 'at1', 'io3n.', 'r1r', 'm1m', 'l1l', 't1t', 's1s', 'a2n', 'an1d', '5nd.', '1p', 'p2h', '1q', '.un1', 'e2x', 'x1c', '2mp', 'om1'], ['ta-ble'], 1, 1], 'Ta-ble'), ('control layout', ['Pentagon', ['1p', 'he2n', '.re1', 'at1', 'm1m', 'r1r', 'e1c', 'hena4', 'pu2', 'gr2', '1tio', 'ex1', 'n1g', '.ta4', 's1s', 'a2n', 'li1', 'n2at'], ['gram-mar', 'pro-ject'], 3, 1], 'Pentagon'), ('control layout', ['hyphenation', ['hy3ph', '1ble', '.re1', 'ter1', 'r1r', 'n1g', 'e2x', 'ca1t', 'pu2', 'om1', 'c2ce', '2mp', 'ex1', 'b2l'], ['ta-ble'], 1, 2], 'hy-phenation')], [('regression: left hyphen minimum', ['Commitment', ['at1', '1m', 'm1m', '4ing.', 'li1', 'he2n', 'e2x', 'e1c', 'l1l', '3ty.', 'ca1t', 'an1d', 'pu2', 'b2l', 's1s', '1na', 'a2n', 'ex1', '2mp', 'hena4', '1ble', 'om1', '1tio', '.re1', 'ter1', 'hen5at', 't1t', '2io', 'c2ce', 'r1r', 'gr2', 'n2at', 'p2h', 'x1c', 'a1b', 'ment1', 'con1', '.ta4', 'io3n.', '1ca', 'n1g', 'o2n', '5nd.', 'hy3ph', '.un1', '1q'], ['mis-sis-sip-pi'], 2, 1], 'Co-m-mit-ment'), ('regression: left hyphen minimum', ['Commitment', ['x1c', 'b2l', 'at1', 'a2n', 'ment1', 'o2n', 'n1g', 'hen5at', 'io3n.', 'e1c', 'e2x', 't1t', '.ta4', 'he2n', 'an1d', 'n2at', '1q', '1p', 'pu2', 'r1r', 'om1', '1ble', 'c2ce', '3ty.', 'con1', '2io', '1m', 'ter1', 'ca1t', '.re1', '2mp', 'p2h', '1na', '.un1', '5nd.', 'l1l', '4ing.', 'hena4', 'm1m', 's1s', 'ex1', 'li1'], [], 3, 2], 'Com-mit-ment'), ('partial-repair probe', ['hyphenation', ['gr2', '1tio', '1q', 'a2n', 'he2n', 'm1m', 'ment1', 'ca1t', 'an1d', '1p', 'io3n.', 'e1c', 'a1b', 'o2n', 'b2l', 'om1'], ['ex-cep-tion', 'mis-sis-sip-pi'], 3, 2], 'hyphena-tion'), ('partial-repair probe', ['category', ['o2n', '1q', '.ta4', 'r1r', 'x1c', 'pu2', 'n2at', '2mp', 'ment1', '1tio', '.re1', 'a2n', '.un1', 'ex1', 'p2h', 'hy3ph', 'b2l', 'c2ce', '1m', 'ca1t', 'm1m', 's1s', '3ty.', 'io3n.', 'a1b', '5nd.', '4ing.', 'l1l', '2io', 'an1d', 't1t', 'li1'], ['ex-cep-tion', 'gram-mar', 'pro-ject'], 3, 3], 'category'), ('right minimum boundary', ['category', ['.ta4', 'a1b', 'b2l', '1ble', 'hy3ph', 'he2n', 'hena4', 'hen5at', '1na', 'n2at', '1tio', '2io', 'o2n', 'pu2', 'ter1', '1m', 'ex1', 'e1c', 'c2ce', 'con1', 'ment1', '4ing.', 'n1g', '.re1', 'gr2', '3ty.', 'li1', '1ca', 'ca1t', 'at1', 'io3n.', 'r1r', 'm1m', 'l1l', 't1t', 's1s', 'a2n', 'an1d', '5nd.', '1p', 'p2h', '1q', '.un1', 'e2x', 'x1c', '2mp', 'om1'], [], 1, 3], 'ca-t-egory'), ('lowercase exception', ['project', ['.ta4', 'a1b', 'b2l', '1ble', 'hy3ph', 'he2n', 'hena4', 'hen5at', '1na', 'n2at', '1tio', '2io', 'o2n', 'pu2', 'ter1', '1m', 'ex1', 'e1c', 'c2ce', 'con1', 'ment1', '4ing.', 'n1g', '.re1', 'gr2', '3ty.', 'li1', '1ca', 'ca1t', 'at1', 'io3n.', 'r1r', 'm1m', 'l1l', 't1t', 's1s', 'a2n', 'an1d', '5nd.', '1p', 'p2h', '1q', '.un1', 'e2x', 'x1c', '2mp', 'om1'], ['pro-ject'], 2, 3], 'pro-ject'), ('control layout', ['table', ['s1s', 'ca1t', '1ca', '.re1', '2io', '1m', 'he2n', 'p2h', 'ment1', 'e1c', '1q', 'c2ce', 'o2n', 'r1r', 'l1l', 't1t', 'hen5at', 'om1', 'ter1', 'hy3ph', 'gr2', 'e2x', '5nd.', '.un1', '1p', 'b2l', 'a1b', 'x1c', 'n2at', '1ble', 'a2n', 'm1m', '1na', 'pu2', '3ty.', 'io3n.', 'ex1', 'con1', 'n1g', 'at1', 'hena4', 'an1d', '1tio', '.ta4', 'li1', '4ing.', '2mp'], ['mis-sis-sip-pi', 'pro-ject'], 1, 1], 'table'), ('control layout', ['announcement', ['1m', 'ex1', '1ca', '3ty.', '2mp', 'c2ce', 'ment1', '1na', 'hy3ph', 'he2n', 'con1', 'n1g', '1ble', 'om1', 'x1c', 'hen5at', 'e2x', 'n2at', 'm1m', 'ter1', '.re1', 'an1d', '1p', '2io', 'e1c', 'p2h', 'hena4', 'b2l', 'gr2', 'l1l'], ['ex-cep-tion'], 1, 2], 'announce-ment')], [('regression: left hyphen minimum', ['battle', ['.un1', 'ter1', 's1s', 'hena4', '3ty.', '1q', 'r1r', 'gr2', 'io3n.', 'om1', 'e1c', '2mp', '1ble', '.ta4', 'at1', 'ex1', 'a1b', 'a2n', 'e2x', 'he2n', 'pu2', 'o2n', '5nd.', 'hy3ph', 'li1', 'an1d', '2io'], [], 3, 1], 'bat-tle'), ('regression: left hyphen minimum', ['Categories', ['1m', 'ter1', '2io', '2mp', 'ex1', 'b2l', 'c2ce', 'gr2', 'li1', 'x1c', 'con1', 'o2n', 's1s', '.re1', 'ca1t'], ['gram-mar', 'pro-ject'], 2, 3], 'Ca-tegories'), ('partial-repair probe', ['Unexpected', ['1tio', 'l1l', 'li1', '1p', 'pu2', 'ter1', 'an1d', '2mp', '.un1', 'hy3ph', 'io3n.', 'a1b', '.re1', 'he2n', '1na', '2io', 't1t', '3ty.', 'ex1', '1m', 'n2at', 'ca1t', 'b2l', 'o2n', '.ta4', 'r1r', 'x1c', 'at1', 'con1', 'e2x', 'c2ce', '1ca', 'n1g', 'hena4', 's1s', 'm1m', 'e1c', '4ing.', '5nd.', 'gr2'], ['ta-ble'], 3, 1], 'Unex-pe-cted'), ('partial-repair probe', ['Categories', ['5nd.', 'he2n', 'hena4', '1q', 'an1d', '.ta4', 'li1', 'r1r', '1tio', 'x1c', 'om1', '.un1', 'ter1', 'n1g', '3ty.', 'gr2', 'con1', '1ca', 'c2ce', '4ing.', 'ment1', 'pu2', 'hen5at', 'a2n', 'ex1', 'm1m', 'io3n.', 't1t', 'ca1t', '1m', 'o2n'], ['pro-ject', 'gram-mar', 'ta-ble'], 3, 1], 'Categories'), ('word-final pattern ing.', ['running', ['.ta4', 'a1b', 'b2l', '1ble', 'hy3ph', 'he2n', 'hena4', 'hen5at', '1na', 'n2at', '1tio', '2io', 'o2n', 'pu2', 'ter1', '1m', 'ex1', 'e1c', 'c2ce', 'con1', 'ment1', '4ing.', 'n1g', '.re1', 'gr2', '3ty.', 'li1', '1ca', 'ca1t', 'at1', 'io3n.', 'r1r', 'm1m', 'l1l', 't1t', 's1s', 'a2n', 'an1d', '5nd.', '1p', 'p2h', '1q', '.un1', 'e2x', 'x1c', '2mp', 'om1'], [], 2, 2], 'running'), ('right minimum boundary', ['category', ['.ta4', 'a1b', 'b2l', '1ble', 'hy3ph', 'he2n', 'hena4', 'hen5at', '1na', 'n2at', '1tio', '2io', 'o2n', 'pu2', 'ter1', '1m', 'ex1', 'e1c', 'c2ce', 'con1', 'ment1', '4ing.', 'n1g', '.re1', 'gr2', '3ty.', 'li1', '1ca', 'ca1t', 'at1', 'io3n.', 'r1r', 'm1m', 'l1l', 't1t', 's1s', 'a2n', 'an1d', '5nd.', '1p', 'p2h', '1q', '.un1', 'e2x', 'x1c', '2mp', 'om1'], [], 1, 3], 'ca-t-egory'), ('control layout', ['understand', ['m1m', '4ing.', '1m', '1q', '1na', 't1t', 'ex1', '.re1'], ['ta-ble', 'mis-sis-sip-pi', 'ex-cep-tion'], 2, 2], 'understand'), ('control layout', ['literally', ['hena4', 'li1', '5nd.', 'om1', 'ex1', 'pu2', '1na', 'ca1t', 'hen5at', 'p2h', 'b2l', 'hy3ph', 's1s', 'ter1'], ['mis-sis-sip-pi'], 1, 3], 'li-ter-ally')]]
for label, args, expected in fixtures[N - 1]:
check(label, solve(args), expected)
print(json.dumps({"observations": observations, "passed": all(x["passed"] for x in observations)}, ensure_ascii=False))
raise SystemExit(0 if all(x["passed"] for x in observations) else 1)
| Boundary fixture | Actual | Expected | Outcome |
|---|---|---|---|
| left minimum boundary | ex-cel-lent | ex-cel-lent | Passed |
| regression: left hyphen minimum | Com-mit-ment | Com-mit-ment | Passed |
| partial-repair probe | Categories | Categories | Passed |
| regression: left hyphen minimum | Com-mit-ment | Com-mit-ment | Passed |
| word-final pattern ing. | running | running | Passed |
| lowercase exception | pro-ject | pro-ject | Passed |
| control layout | Categories | Categories | Passed |
| control layout | Ta-ble | Ta-ble | Passed |
SHA-256 / 440f5faf963a65fe7ba090dc4a6f2d08c49f2b0542bb96ea7c7dc8f0e50e4a64
Verification & scope
A deterministic toy typesetting model with integer widths and a stipulated rule set; it does not claim conformance to any engine. This reproducer isolates one failure mechanism. Results cover the supplied fixtures. Variants within a family share a test contract and should remain grouped when constructing evaluation splits. Related mechanisms with a shared evaluation_group must also remain together; these controlled models are not independent production incidents.
Observations recorded using Python 3.12.14 at 2026-09-29T14:49:48.985164+00:00.
Case digest / d786e8fe06c17ac4dbae419e5da2d0b9990c13ee3a06b067b459526ab51b0f64