\„-parse
näher zu bringen. Denn \“-parse
ist in der Lage, Terminal Steuercodes zu interpretieren, so wie es in C üblich ist. Das kommt in .s
zwar nicht vor, aber übungshalber sei hier auf einen Versuch dazu hingewiesen.
Wird benutzt um die Items auf dem Stack zu zeigen. Es gibt verschieden Arten den Stack darzustellen. Die Gestaltung des Wortes .s
ist also Geschmacksache, bzw. je nach Fragestellung an den Stack auszulegen. So ist es mitunter nützlich sein eigenes .s
zu definieren. Die Sammlung hier kann daher allenfalls dazu anregen, den eigenen Bedürfnissen Ausdruck zu geben.
Minimalistische Darstellung des Stack:
: .s ( i*x -- i*x ) depth 0= ?exit depth 1- for r@ pick . next drop ;
Der Sreenshot dazu sieht dann so aus:
.s ok 11 22 33 44 .s 11 22 33 44 ok
Bei leerem Stack liefert diese Version des .s
also einfach nichts ab. Ansonsten zeigt es die Werte in der Reihenfolge der Eingabe an. Der Vorteil liegt darin, das so eine Ausgabe mit copy&past aus dem Terminal wieder als Eingabe verwendet werden kann. Sei es für das gleiche Terminal, sei es für eine Textverarbeitung - es muss nichts mehr umgestellt werden. Ein sehr forthige Lösung
In dieser Darstellung des Stack werden weitere Informationen mit ausgegeben. Die Werte auf dem Stack werden untereinander aufgelistet, TOP of stack zuerst, und vor dem Wert erscheint die Positionsnummer und die Adresse an der dieser Wert liegt. Das kann beim debuggen eines neuen Systems nützlich sein.
Hier der Code dazu. Quelle: amforth-2.7, file dot-s.asm http://amforth.sourceforge.net/
; ( -- ) Tools ; R( -- ) ; stack dump VE_DOTS: .db $02, ".s",0 .dw VE_HEAD .set VE_HEAD = VE_DOTS XT_DOTS: .dw DO_COLON PFA_DOTS: .dw XT_SP_FETCH .dw XT_DEPTH .dw XT_1MINUS .dw XT_ZERO .dw XT_DOQDO .dw PFA_DOTS2 PFA_DOTS1: .dw XT_DUP .dw XT_I .dw XT_DUP .dw XT_UDOT .dw XT_2STAR .dw XT_PLUS .dw XT_DUP .dw XT_UDOT .dw XT_FETCH .dw XT_UDOT .dw XT_CR .dw XT_DOLOOP .dw PFA_DOTS1 PFA_DOTS2: .dw XT_DROP .dw XT_EXIT
Diese Lösung ist der Minimalistischen nahe, informiert aber immer auch über die Anzahl von Werten auf dem Stack. Die Ausgabe ist auf maxdepth-.s begrenzt. Man sieht also immer nur die obersten Werte. Es können aber viel mehr darauf liegen. Das wird durch die Anzahl <n>
dann deulich gemacht.
Der Versuch .s
des gforth zu entschlüsseln ergab folgendes:
see .s : .s .\" <" depth 0 .r .\" > " depth 0 max maxdepth-.s @ min dup 0 ?DO dup i - pick . LOOP drop ; ok see maxdepth-.s Variable maxdepth-.s see .\" noname : \"-parse type ; latestxt noname : <9152> (compile) type ; latestxt interpret/compile .\" immediate ok
In dieser Definition benutzt gforth .\„
anstelle des .“
Wortes. Warum? Das beleibt Geheimnis der Autoren. 1)
In diesem Beispiel benutzte der Autor S als Symbol für den leeren Stack. Ansonsten ist die Ausgabe dem amforth entsprechend gestaltet. Dort ist allerdings der leere Stack nicht klar bezeichnet, sein BOTTOM
nicht so gut zu erkennen. Zur Kennzeichnung konnte kein B
für bottom genommen werden, da B
als hexadecimale Ziffer verwendet wird. So fiel die Wahl auf S
wie Sockel, oder „auf Grund laufen“ (to strand).
0 21028848 44 1 21028852 33 2 21028856 22 3 21028860 11 S 21028864
: my.s ( -- ) cr depth 0> if depth sp@ swap 0 ( -- adr n 0 ) do ( -- S ) \ S = Strand i . cell+ dup . dup @ ( >< ) . cr loop ( -- adr ) cell+ ( -- adr++ ) else sp@ then ( -- adr ) $53 emit space . ; ( -- :) 11 22 33 44 x.s cr .s \ use gforth .s as reference cr cr
Anmerkung: >< bedeutet byteswap. Das kann nötig sein um eine hi-lo-byte order umzustellen. Siehe auch: big endian, little endian.