Zurück zur Startseite

dc: Programmieren auf einem Stapelsrechner

dc — Unix-Stapelsrechner als Programmiersprache mit Registern, Makros und Rekursion. Der Artikel zerlegt das Stapelmodell, bedingte Konstrukte, FizzBuzz- und Peg-Solitaire-Beispiele mit vollständigem Code.

Programmieren von FizzBuzz auf dc: vom Stapel zum Spiel
Advertisement 728x90

dc: Der Taschenrechner als Programmiersprache für Entwickler

dc ist ein klassischer Unix-Taschenrechner, älter als die Programmiersprache C, und in den Standarddistributionen der meisten Systeme enthalten, einschließlich macOS. Hinter seiner einfachen Fassade verbirgt sich eine vollwertige stapelbasierte Programmiersprache mit Registern, Makros, bedingten Konstrukten und Rekursion. Das Kernmodell ist der Stapel: Zahlen und Zeichenketten werden über Befehle auf den Stapel gelegt, Operatoren entnehmen die obersten Elemente, führen eine Aktion aus und geben das Ergebnis zurück.

Erste Berechnung: Um 2 + 2 zu addieren, geben Sie 2 2 + p ein. Hier schieben 2 2 die Zahlen zeilenweise auf den Stapel, + addiert die beiden obersten Elemente, und p gibt das Ergebnis aus.

2 2 +
p
4

Der Stapel ist das Schlüsselelement: Jedes Literal (Zahl oder [Zeichenkette]) legt einen Wert oben drauf. Kommentare beginnen mit #.

Google AdInline article slot

Arbeiten mit Registern und Variablen

dc bietet 256 Register (a-z, 0-9 und andere Zeichen), die Zahlen oder Zeichenketten speichern. Die Befehle sR speichern das oberste Element des Stapels in Register R, und lR laden es zurück. Register behalten ihren Zustand unabhängig vom Hauptstapel bei.

Beispiel für das Speichern und Wiederherstellen einer Zeichenkette:

[Hallo Welt!] sx
lx
p
Hallo Welt!

Register eignen sich für globale Variablen. Zahlen in Registern werden ähnlich wie auf dem Stapel manipuliert: li lädt i auf den Stapel.

Google AdInline article slot

Makros als Funktionen

Funktionen in dc sind Makros: Zeichenketten, die in Registern gespeichert und mit dem Befehl lRx ausgeführt werden, wobei x das Register ist. Makros werden als [Code] sR definiert.

Beispiel einer Funktion zur Addition der Register a und b:

[la lb +] sS
1 sa
2 sb
lSx
p
3

Makros unterstützen Rekursion und können sich gegenseitig aufrufen, wodurch Unterprogramme entstehen.

Google AdInline article slot

Bedingte Konstrukte

Verzweigungen basieren auf dem Vergleich der beiden obersten Elemente des Stapels. Operatoren umfassen =, >, <, != und andere. Wenn die Bedingung wahr ist, wird das Makro aus dem angegebenen Register ausgeführt.

[[Gleich] p] sE
[[Ungleich] p] sN
1 0
=E
1 0
!=N
Ungleich

Vergleiche verbrauchen zwei Elemente vom Stapel und hinterlassen das Ergebnis (0 oder 1).

Rekursive Schleifen

Es gibt keine Schleifen, aber Rekursion wird über Selbstaufrufe von Makros implementiert. Beispiel für die Ausgabe der Zahlen von 1 bis 10:

[
	li p
	1 + si
	li 11 >C
] sC

1 si
lCx

Makro C gibt i aus, erhöht es und ruft sich selbst rekursiv auf, solange i < 11 ist. Das aktuelle i ist beim Eintritt bereits auf dem Stapel.

  • Vorteile der Rekursion in dc: Einfachheit, keine expliziten Schleifen.
  • Einschränkungen: Risiko eines Stapelüberlaufs bei tiefer Rekursion.
  • Alternativen: Endrekursion minimiert die Stapelnutzung.

FizzBuzz in dc

Die Implementierung von FizzBuzz bis 100 demonstriert eine Kombination aus Makros, Bedingungen und Rekursion. Wichtige Befehle: P (Ausgabe ohne Zeilenumbruch), c (Stapel leeren).

Vollständiger Code:

[[Fizz] P 0 sd] sF
[[Buzz] P 0 sd] sB
[li 3 % 0 =F li 5 % 0 =B] sW
[10 P] sP
[li p c] sD
[
  1 sd
  lWx
  ld 0 =P
  ld 1 =D
  li 1 + si
  li 101 >M
] sM

1 si
lMx

Logik: Flag d bestimmt, ob die Zahl ausgegeben wird. Makro W prüft die Teilbarkeit durch 3/5 und setzt Fizz/Buzz. P mit 10 (LF) für einen Zeilenumbruch.

Fortgeschrittene Anwendungen: Peg Solitaire

dc ermöglicht das Lösen komplexer Aufgaben, wie Peg Solitaire – ein Puzzle mit Sprüngen von Stiften auf einem Brett. Der Brettzustand wird als Binärzahl kodiert, mit Manipulationen über arithmetische und bitweise Operationen (Verschiebungen und Masken sind verfügbar).

Bewegungsvalidierungsformeln in RPN sehen aufgrund bitweiser Prüfungen komplex aus, ermöglichen aber ein vollständiges Spiel: von der Anfangskonfiguration bis zum letzten Stift.

Dieser Ansatz zeigt dc als Werkzeug für Algorithmenprototyping ohne Kompilierung.

Wichtige Erkenntnisse

  • Der Stapel ist die Grundlage aller Operationen: Literale legen drauf, Operatoren entnehmen/legen Ergebnisse.
  • Register (insgesamt 256) für Zustände, Makros für Unterprogramme mit lRx.
  • Bedingungen verbrauchen den Stapel, Rekursion ersetzt Schleifen.
  • p/P für Ausgabe, c zum Leeren, % für Modulo.
  • Geeignet für Skripting, Prototyping und das Erlernen von RPN.

— Editorial Team

Advertisement 728x90

Weiterlesen