Passend zum heutigen Datum habe ich mich mit dem „Haus des Nikolaus“ auseinandergesetzt. Zum Selbststudium lohnt ein Blick auf die Internetseite „Mathematische Basteleien“ von Jürgen Köller, der dort eine umfassende Beschreibung des Problems liefert. Der ebenda gegebene Hinweis, dass man die möglichen Lösungen der Strichführung mittels eines Computerprogramms auch auf einem C64 ermitteln kann, war Anreiz genug, genau dieses zu versuchen. Das Ergebnis wäre vielleicht auch ein passender Beitrag zum aktuell in der Schlußredaktion befindlichen C64-Weihnachtsheft gewesen, wenn das Progrämmchen denn eher verfügbar gewesen wäre.
Die Eingangs erwähnte Internetseite liefert verschiedene Hintergrund-Links und so gibt es auch einen auf ein bereits bestehendes Programm von Matthias Jauernig zur Ermittlung aller existierenden Lösungen. Leider in C und leider – aber nicht verwunderlich – mit rekursiven Funktionsaufrufen. Weil sich das Commodore BASIC dafür nicht wirklich gut eignet, habe ich mich für die Umsetzung am C64 (bzw. C128) lieber an dem an „brute Force“ erinnernden Hinweis aus der zuerst genannten Quelle gehalten.
Um das Haus und die Strichreihenfolge zu beschreiben, werden alle Ecken durchnummeriert. Beginnend unten links mit der Eins geht es gegen den Uhrzeigersinn im Rechteck herum. Die Dachspitze erhält die Fünf. Über eine Verknüpfungsmatrix (wer mit wem) kann man dann definieren, welche Punkte miteinander verbunden sind und welche nicht. Da jede Verbindung nur einmal zulässig ist (also nicht übermalt werden darf) ist die Anzahl der gültigen Lösungen begrenzt.
Das Programm wird dadurch vereinfacht, dass es berücksichtigt – was sich mathematisch ableiten läßt -, dass die Konstruktion des Hauses stets unten links beginnt (Punkt 1) und unten rechts endet (Punkt 2); man kann das umdrehen, erhält dann aber nur ein Spiegelbild. Durch die definierte Start- und Endposition ergibt sich auch für die benachbarten Punkte eine eingeschränkte Variabilität. Über verschachtelte Schleifen und Tabellen hätte man das in einem BASIC-Programm sauber abbilden können, ich habe mich aber für „quick and dirty“ entschieden und alles in eine Schleife gepackt, aus der ich nur die sofort erkennbar ungültigen Werte per IF-Abfrage rausschmeiße. Nicht elegant, nicht schnell, aber es funktioniert (sehr, sehr langsam).
100 rem *** das haus vom nikolaus ***
110 rem
120 dim n(5,5),a(5,5):rem verknuepfungsmatrix
130 data 0,1,1,1,0
140 data 1,0,1,1,0
150 data 1,1,0,1,1
160 data 1,1,1,0,1
170 data 0,0,1,1,0
180 for i=1to5: forj=1to5
190 read a: n(i,j)=a
200 next: next
210 rem start bei 1 ende bei 2
220 rem 9 knoten (0/8), davon 7 variabel
230 dim k(8)
240 k(0)=1:k(8)=2
250 c=0: rem counter
260 rem * hauptschleife *
270 for k=2311111 to 5535554
280 k$=mid$(str$(k),2)
290 f=0: rem fehlerflag
300 fori=1to7
310 k(i)=val(mid$(k$,i,1)):ifk(i)=0 or k(i)>5 then f=1 :i=7
320 next: if f then 450
330 rem * init testmatrix *
340 for i=1to5: forj=1to5
350 a(i,j)=n(i,j)
360 next: next
370 rem * pruefung auf wegstrecken *
380 f=0: rem fehlerflag
390 fori=1to8
400 if a(k(i-1),k(i))=0 then f=1:i=8
410 a(k(i-1),k(i))=0: rem benutzter weg
420 a(k(i),k(i-1))=0: rem zugehoeriger rueckweg
430 next
440 if f=0 then gosub 480
450 next
460 print"*** ende ***"
470 end
480 rem * ausgabe *
490 c=c+1
500 print "loesung"c"{left}:";
510 forj=0to8: print str$(k(j));: next
520 print: return
Es gibt 44 Lösungen (nur so als Hinweis, falls man das Ende der Berechnungen nicht abwarten will). Etwas schneller als in reinem BASIC geht es mit einem Compiler und SuperCPU oder in VICE im Warp-Mode. Der mit BASIC 128 (Data Becker) für einen C128 compilierte Code ist hier verfügbar.
Errata (14.12.2020): Die Zeile 270 sollte wie folgt lauten:
270 for k=2311111 to 4555554