获取Ruby变量

时间:2015-10-10 15:21:12

标签: ruby-on-rails arrays ruby class activerecord

我正在处理一个任务,我得到一组类(ActiveRecord类更精确),我想得到他们的名字。我这样做是通过迭代这个集合并将#name之类的方法应用于集合的元素。 像这样:

array_of_classes.map {|class| class.name}

问题是这个数组中的一些元素没有被初始化,所以当我在它们上面调用#name时,我得到了:

NameError: uninitialized constant ClassName

要确定是否已启用变量或常量,我可以使用defined?关键字,如下所示:

> defined? UnInitializedClass
nil
> defined? InitializedClass
"constant"

这个问题是当我们有一个两个初始化和未初始化元素的数组时,事情变得更复杂,我们遍历数组来获取它们的元素。 defined?关键字将应用于迭代器本身,而不是应用于这些变量所指向的类(或常量或变量)。

> [UnInitializedClass, InitializedClass ].map {|x| defined? x}
["local-variable", "local-variable"]

有没有办法在变量defined?保留的constant上应用x关键字?

如果没有,您是否知道如何找到Ruby数组的未初始化元素?

另一个想法可能是使用方括号方法[]访问每个元素,但defined?仍未应用于引用的常量

> defined? array[0]
"method"
> defined? array[1]
"method"

3 个答案:

答案 0 :(得分:2)

或更短版本的pdobb代码:

array_of_classes.map {|klass| klass.name rescue nil}.compact

答案 1 :(得分:1)

我不确定如何拥有一系列常量,其中一些常量未定义......但是,您可以使用一个救援块来过滤掉有效常量。

array_of_classes = 
  array_of_classes.each_with_object([]) { |klass, acc|
    begin
      klass
    rescue NameError
      # Do nothing
    else
      acc << klass
    end
  }

之后你应该按照惯例使用常量。

答案 2 :(得分:1)

这个问题唯一有意义的方法是数组不包含常量和未初始化的常量(后者会立即引发语法错误),但包含初始化未初始化类名称的字符串。在这种情况下,你可以这样做:

class A
end 
B = 'cat'

['A','B','C'].select do |s|
  Object.const_defined?(s) ? Object.const_get(s).is_a?(Class) : false
end
  #=> ["A"]

请注意,这通常涉及课程,而不仅仅是特定课程。