Интерактивная игра
В Gforth вы можете играть с does>
интерпретируя.
create foo 123 ,
foo @ . \ prints 123
does> ( addr -- ) @ . ;
foo \ prints 123
does> ( addr -- ) @ 1+ . ;
foo \ prints 124
' foo >body @ . \ prints 123
Итак, does>
просто изменяет поведение последнего слова, когда это последнее слово определено через create
. Будет ошибкой запускать does>
, когда последнее слово не было определено через create
.
Использование на практике
Обычно does>
используется для установки нового поведения только один раз для слова, определенного через create
. Возможность изменить это поведение несколько раз — это лишь побочный эффект исторической реализации, и на практике этот эффект почти не используется.
Альтернативные способы
На практике случаи, когда используется does>
, могут быть реализованы и без does>
.
Например, пусть мы хотим реализовать слово counter
, которое создает счетчик, который каждый раз возвращает следующее значение и используется следующим образом:
1 counter x1
x1 . \ prints 1
x1 . \ prints 2
x1 . \ prints 3
Реализация через create
does>
: counter ( x0 "ccc" -- ) \ Run-Time: ( -- x )
create , does> ( addr -- x ) dup >r @ dup 1+ r> !
;
Реализация с использованием цитирования
[undefined] lit, [if] : lit, ( x -- ) postpone lit, ; [then]
[undefined] xt, [if] : xt, ( xt -- ) compile, ; [then]
: counter ( x0 "ccc" -- ) \ Run-Time: ( -- x )
align here >r , [: ( addr -- x ) dup >r @ dup 1+ r> ! ;] >r
: r> r> lit, xt, postpone ;
;
Реализация с использованием макроса (встраивание кода) через слово ]]
:
: counter ( x0 "ccc" -- ) \ Run-Time: ( -- x )
align here >r ,
: r> lit, ]] dup >r @ dup 1+ r> ! [[ postpone ;
;
person
ruvim
schedule
20.11.2020