nonopolarity
nonopolarity

Reputation: 151214

How to change verbose code in Ruby to simpler code using Metaprogramming?

It is said that Ruby is a metaprogramming language. I wonder if the first 3 lines can be made less verbose using metaprogramming?

RUBY_VERSION ||= "unknown version"
RUBY_PATCHLEVEL ||= "unknown patchlevel"
RUBY_PLATFORM ||= "unknown platform"

print "Ruby ", RUBY_VERSION, " patch ", RUBY_PATCHLEVEL, " on ", RUBY_PLATFORM

Upvotes: 1

Views: 244

Answers (2)

samuil
samuil

Reputation: 5081

I think that you shouldn't change value of constants. Instead try this:

puts "Ruby #{RUBY_VERSION || 'unknown version'}" # ...

Also, using Rails goodies, you could improve Peter's solution by calling

"RUBY_#{v}".constantize

instead of dirty eval ;-)

Upvotes: 0

Peter
Peter

Reputation: 132377

This does the job:

%w{version patchlevel platform}.each{|v| eval "RUBY_#{v.upcase} ||= 'unknown #{v}'"}

but I think it's opaque and unpleasant. I think your original version is much better. In particular, I think ||= with constants isn't great anyway (since constants shouldn't be dynamic), and that using eval with constants is not standard or therefore expected. Putting conditional assignment, constants and eval all together makes for a bad mix, in my opinion.

Upvotes: 3

Related Questions