!752 static BWImage bw; static ImageSurface imageSurface; static Reproducer reproducer; !include #1000522 // image helper functions p { bw = loadBWImage("#1004541"); imageSurface = showImage(bw.getBufferedImage()); reproducer = new RandomSolid; reproduceOpenEnd(bw, imageSurface); } interface Reproducer { public S reproduce(BWImage original); } static class Solid extends Params { float col; Solid copy() { new Solid p; baseClone(p); p.col = col; return p; } public String toString() { return "Solid " + formatDouble(col, 2); } BWImage render() { int w = originalImage.getWidth(), h = originalImage.getHeight(); return new BWImage(w, h, col); } } static class RandomSolid implements Reproducer { int n = -1; public S reproduce(BWImage original) { ++n; DynamicObject p = new DynamicObject("Solid"); if (n % 2 == 0) { p.put("col", randomBrightness()); } else { p.put("col", probeRandomPixel(original)); } ret structure(p); } } static abstract class Params { BWImage originalImage; abstract BWImage render(); abstract Params copy(); void baseClone(Params p) { p.originalImage = originalImage; } BWImage rendered; BWImage getImage() { if (rendered == null) rendered = render(); return rendered; } Double score; double getScore() { if (score == null) score = calcScore(); return score; } double calcScore() { return 100*(1-diff(originalImage, getImage())); } boolean isBetterThan(Params p) { return getScore() > p.getScore(); } } static S reproduce(BWImage original) { ret reproducer.reproduce(original); } static void reproduceOpenEnd(BWImage original, ImageSurface imageSurface) { S bestDesc = null; Params best = null; long lastPrint = 0, lastN = 0; for (long ntry = 1; ; ntry++) { ping(); long now = now(); if (now >= lastPrint+1000) { long tps = (ntry-lastN)*1000/(now-lastPrint); lastPrint = now; lastN = ntry; String s = "Try " + ntry + " (" + tps + "/s)"; if (best == null) System.out.println(s); else { System.out.println("Best: " + bestDesc); System.out.println(s + ", score: " + formatDouble(best.getScore(), 2) + "%, structure size: " + structureSize(best, Params.class)); } } S desc; try { desc = reproduce(original); } catch e { print("Production failed: " + exceptionToStringShort(e)); continue; } Params p; try { p = makeParams(original, desc); } catch { print("Can't unstructure: " + desc); continue; } if (bestDesc == null || p != null && p.getScore() > best.getScore()) { //System.out.println("New best! " + p.getScore()); bestDesc = desc; best = p; imageSurface.setImage(p.getImage().getBufferedImage()); } if (p != null && p.getScore() >= 100.0) break; } } static Params makeParams(BWImage original, S desc) { Params p = cast unstructure(desc); p.originalImage = original; ret p; }