在ruby中,如果我“需要foo”,有没有办法随后确定foo.rb中定义的模块的名称?
例如,假设我有一个名为foo.rb的ruby文件,如下所示:
# foo.rb
module MyModule
def self.summary
"this does something useful"
end
...
end
在另一个脚本中,在我执行“require foo”之后,如何确定我现在有一个名为MyModule的模块?
我所追求的最终目标是能够做到这样的事情:
file = someComputedFileName()
require file
puts "summary of #{file}: #{???::summary}
虽然我可以强制自己使模块名称和文件名相同,但我宁愿不这样做。我希望在制作短文件名方面有更多的自由,但是更具表现力的模块名称。但是,我向自己保证每个文件只定义一个模块(想想:插件)。
答案 0 :(得分:4)
我不知道这是否是最好的解决方案,但我认为这似乎有用:
all_constants = Object.constants
require 'foo'
foo_constants = Object.constants - all_constants
foo_constants应该只提供由foo.rb定义的模块,类或其他常量。
答案 1 :(得分:3)
一种方法是在需要文件之前使用ObjectSpace。each_object(Module)查找所有已定义的模块。然后,在需要文件后,再次遍历所有已定义的模块,看看是否有新的模块。
require "set"
old_modules = SortedSet.new
ObjectSpace.each_object(Module) {|m| old_modules.add(m) }
file = someComputedFileName()
require file
new_modules = SortedSet.new
ObjectSpace.each_object(Module) {|m| new_modules.add(m) unless old_modules.include?(m) }
puts "summary of #{file}: #{new_modules.to_a.map{|m|m.summary}.join(',')}"
这也可以让你在文件中定义多个模块。