收集不必要分配给任何变量/常量的对象 [英] Collecting objects that are not necessarly assigned to any variables/constants
问题描述
未分配给任何变量/常数的对象会立即消失(在正常情况下).在下面的第三行中,字符串"foo"
未被ObjectSpace.each_object(String)
捕获:
Objects that are not assigned to any variable/constant disappear immediately (under normal circumstance). In the following, the string "foo"
is not captured by ObjectSpace.each_object(String)
in the third line:
strings = ObjectSpace.each_object(String).to_a
"foo"
ObjectSpace.each_object(String).to_a - strings # => []
是否可以捕获不必要分配给任何变量/常量或部分变量/常量的对象?我对捕获字符串特别感兴趣.相关域可以是文件或块.我期望如下所示:
Is it possible to capture objects that are not necessarly assigned to any variables/constants or part of any variables/constants? I am particularly interested in capturing strings. The relevant domain can be a file, or a block. I expect something like the following:
capture_all_strings do
...
"a"
s = "b"
@s = "c"
@@s = "d"
S = "e"
%q{f}
...
end
# => ["a", "b", "c", "d", "e", "f"]
推荐答案
Ruby在解析文件时会创建字符串实例.这是一个示例:字符串
Ruby creates the string instances when parsing your file. Here's an example: the string
"aaa #{123} zzz"
解析为:
$ ruby --dump=parsetree -e '"aaa #{123} zzz"'
###########################################################
## Do NOT use this node dump for any purpose other than ##
## debug and research. Compatibility is not guaranteed. ##
###########################################################
# @ NODE_SCOPE (line: 1)
# +- nd_tbl: (empty)
# +- nd_args:
# | (null node)
# +- nd_body:
# @ NODE_DSTR (line: 1)
# +- nd_lit: "aaa "
# +- nd_next->nd_head:
# | @ NODE_EVSTR (line: 1)
# | +- nd_body:
# | @ NODE_LIT (line: 1)
# | +- nd_lit: 123
# +- nd_next->nd_next:
# @ NODE_ARRAY (line: 1)
# +- nd_alen: 1
# +- nd_head:
# | @ NODE_STR (line: 1)
# | +- nd_lit: " zzz"
# +- nd_next:
# (null node)
在解析器阶段有两个字符串文字,"aaa "
和" zzz"
:
There are two string literals at the parser stage, "aaa "
and " zzz"
:
# +- nd_lit: "aaa "
# ...
# | +- nd_lit: " zzz"
检查ObjectSpace
确认这些字符串已被实例化:
Inspecting ObjectSpace
confirms that these strings have been instantiated:
$ ruby -e '"aaa #{123} zzz"; ObjectSpace.each_object(String) { |s| p s }' | egrep "aaa|zzz"
"\"aaa \#{123} zzz\"; ObjectSpace.each_object(String) { |s| p s }\n"
"aaa 123 zzz"
" zzz"
"aaa "
因此,除非您要创建新的字符串实例(例如,通过将字符串文字赋值给变量),否则无法检测到字符串的创建.执行代码时已经存在.
So unless you are creating a new string instance (e.g. by assigning the string literal to a variable) you can't detect the string creation. It's already there when the code is being executed.
这篇关于收集不必要分配给任何变量/常量的对象的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!