如何检查Ruby中的类是否已经存在

时间:2022-05-05 23:44:16

How do I check if a class already exists in Ruby?

如何检查Ruby中是否已经存在类?

My code is:

我的代码是:

puts "enter the name of the Class to see if it exists"   
nameofclass=gets.chomp  
eval (" #{nameofclass}......  Not sure what to write here")

I was thinking of using:

我想用:

eval "#{nameofclass}ancestors.     ....."

12 个解决方案

#1


69  

You can use Module.const_get to get the constant referred to by the string. It will return the constant (generally classes are referenced by constants). You can then check to see if the constant is a class.

您可以使用模块。const_get获取字符串引用的常量。它将返回常量(通常类由常量引用)。然后可以检查常量是否为类。

I would do something along these lines:

我会做一些类似的事情:

def class_exists?(class_name)
  klass = Module.const_get(class_name)
  return klass.is_a?(Class)
rescue NameError
  return false
end

Also, if possible I would always avoid using eval when accepting user input; I doubt this is going to be used for any serious application, but worth being aware of the security risks.

而且,如果可能的话,在接受用户输入时,我总是避免使用eval;我怀疑这是否会用于任何严肃的应用程序,但值得注意安全风险。

#2


42  

perhaps you can do it with defined?

也许你能用定义来做?

eg:

例如:

if defined?(MyClassName) == 'constant' && MyClassName.class == Class  
   puts "its a class" 
end

Note: the Class check is required, for example:

注意:需要进行类检查,例如:

Hello = 1 
puts defined?(Hello) == 'constant' # returns true

To answer the original question:

回答最初的问题:

puts "enter the name of the Class to see if it exists"
nameofclass=gets.chomp
eval("defined?(#{nameofclass}) == 'constant' and #{nameofclass}.class == Class")

#3


24  

You can avoid having to rescue the NameError from Module.const_get if you are looking the constant within a certain scope by calling Module#const_defined?("SomeClass").

您可以避免不得不从模块中挽救NameError。如果您正在通过调用模块#const_defined?(“SomeClass”)在某个范围内查找常量,那么请使用const_get。

A common scope to call this would be Object, eg: Object.const_defined?("User").

调用它的通用范围是Object,例如:Object.const_defined?(“User”)。

See: "Module".

看:“模块”。

#4


11  

defined?(DatabaseCleaner) # => nil
require 'database_cleaner'
defined?(DatabaseCleaner) # => constant

#5


7  

Class names are constants. You can use the defined? method to see if a constant has been defined.

类名是常数。你可以用定义的吗?方法,查看是否定义了常数。

defined?(String)    # => "constant"
defined?(Undefined) # => nil

You can read more about how defined? works if you're interested.

你可以阅读更多关于如何定义?如果你感兴趣的工作。

#6


6  

Here's a more succinct version:

这里有一个更简洁的版本:

def class_exists?(class_name)
  eval("defined?(#{class_name}) && #{class_name}.is_a?(Class)") == true
end

class_name = "Blorp"
class_exists?(class_name)
=> false

class_name = "String"
class_exists?(class_name)
=> true

#7


6  

Kernel.const_defined?("Fixnum") # => true

#8


3  

Here's something I sometimes do to tackle this very issue. You can add the following methods to the String class like so:

我有时会做一些事情来解决这个问题。可以向String类添加以下方法:

class String
    def to_class
        Kernel.const_get self
    rescue NameError 
        nil
    end

    def is_a_defined_class?
        true if self.to_class
    rescue NameError
        false
    end
end

Then:

然后:

'String'.to_class
=> String
'unicorn'.to_class
=> nil
'puppy'.is_a_defined_class?
=> false
'Fixnum'.is_a_defined_class?
=> true

#9


1  

I used this to see if a class was loaded at runtime:

我使用它来查看一个类是否在运行时加载:

def class_exists?(class_name)
  ObjectSpace.each_object(Class) {|c| return true if c.to_s == class_name }
  false
end

#10


1  

In just one line, I would write:

只要一行,我就会写:

!!Module.const_get(nameofclass) rescue false

that will return trueonly if the given nameofclass belongs to a defined class.

只有当给定的nameofclass属于一个定义的类时,才会返回true。

#11


0  

I assume you'll take some action if the class is not loaded.

我假设如果没有加载类,您将采取一些操作。

If you mean to require a file, why not just check the output of require?

如果您想要一个文件,为什么不检查需要的输出?

require 'already/loaded'  
=> false

#12


0  

If you want something packaged, the finishing_moves gem adds a class_exists? method.

如果您希望打包某些东西,那么finishing_moves gem添加了class_exist吗?方法。

class_exists? :Symbol
# => true
class_exists? :Rails
# => true in a Rails app
class_exists? :NonexistentClass
# => false

#1


69  

You can use Module.const_get to get the constant referred to by the string. It will return the constant (generally classes are referenced by constants). You can then check to see if the constant is a class.

您可以使用模块。const_get获取字符串引用的常量。它将返回常量(通常类由常量引用)。然后可以检查常量是否为类。

I would do something along these lines:

我会做一些类似的事情:

def class_exists?(class_name)
  klass = Module.const_get(class_name)
  return klass.is_a?(Class)
rescue NameError
  return false
end

Also, if possible I would always avoid using eval when accepting user input; I doubt this is going to be used for any serious application, but worth being aware of the security risks.

而且,如果可能的话,在接受用户输入时,我总是避免使用eval;我怀疑这是否会用于任何严肃的应用程序,但值得注意安全风险。

#2


42  

perhaps you can do it with defined?

也许你能用定义来做?

eg:

例如:

if defined?(MyClassName) == 'constant' && MyClassName.class == Class  
   puts "its a class" 
end

Note: the Class check is required, for example:

注意:需要进行类检查,例如:

Hello = 1 
puts defined?(Hello) == 'constant' # returns true

To answer the original question:

回答最初的问题:

puts "enter the name of the Class to see if it exists"
nameofclass=gets.chomp
eval("defined?(#{nameofclass}) == 'constant' and #{nameofclass}.class == Class")

#3


24  

You can avoid having to rescue the NameError from Module.const_get if you are looking the constant within a certain scope by calling Module#const_defined?("SomeClass").

您可以避免不得不从模块中挽救NameError。如果您正在通过调用模块#const_defined?(“SomeClass”)在某个范围内查找常量,那么请使用const_get。

A common scope to call this would be Object, eg: Object.const_defined?("User").

调用它的通用范围是Object,例如:Object.const_defined?(“User”)。

See: "Module".

看:“模块”。

#4


11  

defined?(DatabaseCleaner) # => nil
require 'database_cleaner'
defined?(DatabaseCleaner) # => constant

#5


7  

Class names are constants. You can use the defined? method to see if a constant has been defined.

类名是常数。你可以用定义的吗?方法,查看是否定义了常数。

defined?(String)    # => "constant"
defined?(Undefined) # => nil

You can read more about how defined? works if you're interested.

你可以阅读更多关于如何定义?如果你感兴趣的工作。

#6


6  

Here's a more succinct version:

这里有一个更简洁的版本:

def class_exists?(class_name)
  eval("defined?(#{class_name}) && #{class_name}.is_a?(Class)") == true
end

class_name = "Blorp"
class_exists?(class_name)
=> false

class_name = "String"
class_exists?(class_name)
=> true

#7


6  

Kernel.const_defined?("Fixnum") # => true

#8


3  

Here's something I sometimes do to tackle this very issue. You can add the following methods to the String class like so:

我有时会做一些事情来解决这个问题。可以向String类添加以下方法:

class String
    def to_class
        Kernel.const_get self
    rescue NameError 
        nil
    end

    def is_a_defined_class?
        true if self.to_class
    rescue NameError
        false
    end
end

Then:

然后:

'String'.to_class
=> String
'unicorn'.to_class
=> nil
'puppy'.is_a_defined_class?
=> false
'Fixnum'.is_a_defined_class?
=> true

#9


1  

I used this to see if a class was loaded at runtime:

我使用它来查看一个类是否在运行时加载:

def class_exists?(class_name)
  ObjectSpace.each_object(Class) {|c| return true if c.to_s == class_name }
  false
end

#10


1  

In just one line, I would write:

只要一行,我就会写:

!!Module.const_get(nameofclass) rescue false

that will return trueonly if the given nameofclass belongs to a defined class.

只有当给定的nameofclass属于一个定义的类时,才会返回true。

#11


0  

I assume you'll take some action if the class is not loaded.

我假设如果没有加载类,您将采取一些操作。

If you mean to require a file, why not just check the output of require?

如果您想要一个文件,为什么不检查需要的输出?

require 'already/loaded'  
=> false

#12


0  

If you want something packaged, the finishing_moves gem adds a class_exists? method.

如果您希望打包某些东西,那么finishing_moves gem添加了class_exist吗?方法。

class_exists? :Symbol
# => true
class_exists? :Rails
# => true in a Rails app
class_exists? :NonexistentClass
# => false