我们说我有一些rebol / red代码。如果我加载源文本,我会得到一个块,但如何从块中获取源文本?我尝试过form block但它没有回复源文本。
text: {
Red [Title: "Red Pretty Printer"]
out: none ; output text
spaced: off ; add extra bracket spacing
indent: "" ; holds indentation tabs
emit-line: func [] [append out newline]
emit-space: func [pos] [
append out either newline = last out [indent] [
pick [#" " ""] found? any [
spaced
not any [find "[(" last out find ")]" first pos]
]
]
]
emit: func [from to] [emit-space from append out copy/part from to]
clean-script: func [
"Returns new script text with standard spacing."
script "Original Script text"
/spacey "Optional spaces near brackets and parens"
/local str new
] [
spaced: found? spacey
clear indent
out: append clear copy script newline
parse script blk-rule: [
some [
str:
newline (emit-line) |
#";" [thru newline | to end] new: (emit str new) |
[#"[" | #"("] (emit str 1 append indent tab) blk-rule |
[#"]" | #")"] (remove indent emit str 1) break |
skip (set [value new] load/next str emit str new) :new
]
]
remove out ; remove first char
]
print clean-script read %clean-script.r
}
block: load text
答案 0 :(得分:6)
LOAD是一种具有复杂行为的高级操作,例如它可以带一个文件!,一个STRING!或一个块!因为它做了很多不同的事情,所以很难说它作为一种操作的确切补充。 (例如,当你从文件中加载时,SAVE似乎是"反向")
但你的例子是专门处理STRING!:
如果我加载源文本,我会得到一个块,但如何从块中取回源文本?
总的来说,非常相关的事情:你不能回来"源文本。
在上面的示例中,源文本包含注释,在LOAD之后它们将消失。此外,以每个值携带的NEW-LINE标志的形式保留非常有限量的空白信息。然而,您使用的具体缩进样式 - 或者您是否使用了制表符或空格 - 并未保留。
更微妙地说,少量的符号区分会丢失。串!加载的文字将失去你是否写下"with quotes"
或{with curly braces}
的知识...... Rebol和Red都没有保留这一点。 (即使他们这样做了,也不会回答突变后或新字符串后要做什么的问题。)日期有变化!输入格式,并不记得您使用的具体格式。等
但是当谈到将代码往返作为文本时,与绑定相比,格式化是微不足道的。考虑一下你可以构建如下结构:
>> o1: make object! [a: 1]
>> o2: make object! [a: 2]
>> o3: make object! [a: 3]
>> b: compose [(in o1 'a) (in o2 'a) (in o3 'a)]
== [a a a]
>> reduce b
[1 2 3]
>> mold b
"[a a a]"
您不能简单地将 b 序列化为字符串"[a a a]"
,并且有足够的信息来获取等效的来源。 Red比Rebol更能掩盖这种影响 - 因为甚至像STR to block!
这样的操作!并且system/lexer/transcode
似乎绑定到用户上下文。但是,除了最微不足道的例子之外,你将面临的问题是什么。
Rebol2和Red有一些二进制格式试图解决这个问题。例如在" RedBin" a WORD! saves its context (以及该上下文的索引)。但是,您必须考虑要将多少加载环境拖入文件以保留上下文。所以它肯定会打开一堆蠕虫。
这并不是说模仿出来的能力并没有帮助。但是没有免费午餐......所以Rebol和Red程序最终不得不像其他人一样考虑序列化。如果您正在考虑对任何源代码进行处理 - 出于注释保存的原因(如果没有别的话) - 那么PARSE应该是您要达到的第一件事。