我试图将字符串值存储到变量中。要定义这个变量,我使用:
: define CREATE 0 , ;
define x
我可以很容易地存储一个整数/浮点值到x
使用
10 x !
或
10.0e x f!
我使用@
或f@
来访问它。现在我试图存储一个字符串值:
s" hello world" x !
这样做的问题是它将两个值推送到堆栈(因为它是一个计数字符串),但x !
只会将项目存储在顶部,这是字符串的长度。这是很危险的,因为在引用x
的时候,堆栈内容可能已经被修改了,使得地址不直接低于长度(坏!),所以type
会失败。所以我的问题是,有没有一种方法来存储两个值(地址和长度)到x
?或者有不同的数据类型/操作数可以让我实现这一点?
任何帮助都是感激的。
实现此功能所需的许多东西与您已经拥有的非常方便。
如果你想在你创建的东西中存储两个值,你需要一个不同版本的define
;
: 2define create 0 , 0 , ;
把"2"放在单词的开头是一种惯例,表示它和没有"2"的单词做同样的事情,但在双单元格的东西上做同样的事情。
你可以这样写:
2define 2x
//Write something to 2x
s" Hello world!" 2x 2!
//Retrieve it and print
2x 2@ type
值得注意的是,s"
返回的地址是去年项目的持续时间不能保证,可能会覆盖s"
以后使用,看到一个方法,使一个字符串变量,保证最后看看这个答案https://stackoverflow.com/a/8748192/547299(它长了一点喘气的但有一个定义的一个词叫string
说明)。
不要被"!"卡住。这是更有效的…
: 2x S" Hello World!" ;
同样,define对于浮点数是不安全的,它可以是
: define CREATE 0 f, does> f@ ;
3.1459e0 define pi
pi f. 3.1459 ok
Gforth有一个$! ( c-addr u addr -- )
字正是为了这个目的。给定一个字符串和一个地址,它将字符串复制到一个新的分配空间并在地址处存储字符串。如果地址是已经存储了一个字符串,该字符串将被释放。
:
define x
s" hello world" x $!
x $@ type hello world
您还可以使用固定缓冲区来存储计数字符串和单词,如PLACE和+PLACE,它们具有$!
相同的堆栈图片。同样对于上述内容(尽管有字符限制):
256 buffer: x
s" hello world" x place
x count type hello world
s" !" x +place
x count type hello world!
不能将字符串存储在Forth意义上的VARIABLE中。变量最多有2个4或8个长度字符串的空间,这取决于Forth。你必须把每一个字符都存储在"因为字符串是易变的,以后通过指针访问可以发现内容发生了变化。如果你想存储一个字符串,你需要一个缓冲区。缓冲区必须至少比字符串长(废话!),字符串的长度必须与它一起存储,以适应字符串的正常含义。除了分配正确大小的缓冲区之外,还必须执行以下操作:
1024 CONSTANT SIZE Pray this is enough
CREATE BUFFER SIZE ALLOT
"AAP" BUFFER $!
加引号的字符串是2012标准,留下(地址,长度)。美元!留作练习。^ H ^ ^ H ^ ^ H ^ H
: $! ( cs s -- ) 2DUP ! CELL+ SWAP CMOVE ;