!752 please include function img_upperWidthToLowerWidth. please include function img_averageWidthDividedByHeight. please include function img_centralPixelSet. please include function img_leftishness. sS font = "#1004569"; static float size = 40f; static BWImage render(S text) { ret autoCroppedBWImage(renderText(font, size, text)); } p { BWImage zero = autoCroppedBWImage(renderText(font, size, "0")); BWImage one = autoCroppedBWImage(renderText(font, size, "1")); showBWImage(zero); showBWImage(one); Map> ranges = new TreeMap; for (size = 10f; size <= 60f; size++) analyze(ll(render("0"), render("1")), ranges, "upperWidthToLowerWidth averageWidthDividedByHeight centralPixelSet leftishness"); //printStruct(ranges); for (S key : keys(ranges)) { L l = ranges.get(key); if (rangesOverlap(l)) print("bad: " + key); else print("good! " + key); } } svoid analyze(L images, Map> ranges, S functions) { for (S f : splitAtSpace(functions)) { L l = ranges.get(f); if (l == null) ranges.put(f, l = new L); for i over images: { BWImage img = images.get(i); float val = 0f; try { val = toFloat(call(mc(), "img_" + f, img)); } catch e { printShortException(e); } listSet(l, i, addToRange(get(l, i), val), null); } } } // can overwrite original object static Range addToRange(Range r, float val) { if (r == null) ret new Range(val); if (r.min > r.max) r.min = r.max = val; else { if (val < r.min) r.min = val; if (val > r.max) r.max = val; } ret r; } static bool rangesOverlap(Range a, Range b) { ret intersectRanges(a, b) != null; } static Range intersectRanges(Range a, Range b) { float min = max(a.min, b.min); float max = min(a.max, b.max); ret min <= max ? new Range(min, max) : null; } static bool rangesOverlap(L l) { assertTrue(l(l) == 2); ret rangesOverlap(first(l), last(l)); }