19
const = :FOO FOO = :ok defined? FOO => 'constant' 

How to check if FOO is defined using const?

defined? eval( const.to_s ) 

does not work.

5
  • possible duplicate of Check if a constant is already defined Commented Jul 7, 2015 at 1:21
  • 1
    @vgoff: Not a duplicate to that. The linked question gives defined? FOO, not Object.const_defined? :FOO that is required here. The key phrase in the question is "by its symbol", by which it differs from the linked question. Commented Jul 7, 2015 at 2:35
  • You are converting the symbol to a string, in your question, so I am not sure how the symbol can be 'key'. But if the key phrase is the eval, then I will agree it is a different question. Commented Jul 7, 2015 at 4:09
  • 1
    This question is obviously different from stackoverflow.com/questions/10171978/…. The previously answered question does not assign a variable to the constant. And, I even showed how the accepted answer does not work in this case. Commented Jul 7, 2015 at 12:03
  • 1
    This is not a duplicate question. The accepted answer to the linked question (checking with defined?) will not work if you have the constant name stored in a string/symbol variable and want to know if it is defined. i.e. v = 'MyConstant'; defined? v; # => "local-variable" regardless of whether MyConstant is defined or not. Likewise defined? v.constantize; # => "method" regardless. Collin Graves accepted answer, with Object.const_defined?, is a good workaround. Commented Feb 11, 2016 at 9:49

2 Answers 2

35

Use const_defined? instead: http://ruby-doc.org/core/classes/Module.html#M000487

Object.const_defined?(const.to_s) 
Sign up to request clarification or add additional context in comments.

2 Comments

Can also just do Object.const_defined?(const) since const is a symbol, and const_defined?() accepts either a symbol or string.
Calling to_s on the value supplied to Object.const_defined? is good practice for any generalized solution. For example: ruby >>> Object.const_get(nil) # => TypeError: no implicit conversion of nil into String >>> Object.const_get(nil.to_s) # => NameError: wrong constant name >>> Object.const_get(Hash) # => TypeError: no implicit conversion of Class into String >>> Object.const_get(Hash.to_s) # => Hash
1
const = :FOO FOO = :OK defined?(FOO) # => "constant" instance_eval("defined?(#{const})") # => "constant" 

This will evaluate the statement, and gets around limitations to how defined? works in that it does not evaluate anything, so we have to evaluate it before it gets the instruction to call defined?.

Your eval is simply in the wrong order.

1 Comment

Right, it is the same idea. Just a difference of scope. It is why I said that your eval was in the wrong order, it was implying that you could use eval like you originally posted.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.