[lnkForumImage]
TotalShareware - Download Free Software

Confronta i prezzi di migliaia di prodotti.
Asp Forum
 Home | Login | Register | Search 


 

Forums >

comp.lang.ruby

load a Ruby source with params

Cyril Beer

2/16/2009 1:19:00 PM

Hello, Ruby world,

Do you know how loading a Ruby source with parameters? I had try so by
using:
load(my_file my_arg)

but it do not seems to work...

Thank you.
--
Posted via http://www.ruby-....

6 Answers

Brian Candler

2/16/2009 4:08:00 PM

0

Sai Hl wrote:
> Do you know how loading a Ruby source with parameters? I had try so by
> using:
> load(my_file my_arg)
>
> but it do not seems to work...

I think you're confusing two things.

(1) Loading in more Ruby code to the currently-running Ruby interpreter.
This is done using "load" or "require". There is no concept of
"parameters" here. However you could set a global variable (e.g. $foo)
or a constant (Foo), which the code in the other file makes use of.

But it would be more normal for the other file just to define modules or
classes, and then after the load has completed you invoke one of those
modules or classes, at which point you can pass whatever parameters you
like.

(2) Forking and execing a new child process. This could be another
Ruby interpreter, but it could also be any other program on your system.
When you do this, you can pass command-line arguments (and/or
environment variables and open files)

The simplest way is with Kernel#system, e.g.

system("/bin/prog","arg1","arg2")

but other options include backticks, IO.popen, the open3 and open4
libraries, and the low-level Kernel#fork and Kernel#exec calls.
--
Posted via http://www.ruby-....

Cyril Beer

2/16/2009 6:39:00 PM

0

Brian Candler wrote:
> (1) Loading in more Ruby code to the currently-running Ruby interpreter.
> This is done using "load" or "require". There is no concept of
> "parameters" here. However you could set a global variable (e.g. $foo)
> or a constant (Foo), which the code in the other file makes use of.
>
> But it would be more normal for the other file just to define modules or
> classes, and then after the load has completed you invoke one of those
> modules or classes, at which point you can pass whatever parameters you
> like.
>
> (2) Forking and execing a new child process. This could be another
> Ruby interpreter, but it could also be any other program on your system.
> When you do this, you can pass command-line arguments (and/or
> environment variables and open files)
>
> The simplest way is with Kernel#system, e.g.
>
> system("/bin/prog","arg1","arg2")
>
> but other options include backticks, IO.popen, the open3 and open4
> libraries, and the low-level Kernel#fork and Kernel#exec calls.

Many thanks for your detailled answer, Brian Candler.

until now I used those few lines:

# inc.test.rb
'Hello ' + subject

# inc.other_test.rb
'Hi, ' + subject

# main.rb
@files = []
subject = 'World'
Dir['inc.*.rb'].each do |file|
open(file) { |f| @files << f.read }
end
@files.each { |f| puts "#{eval(f)}" }

But it's true that the eval function takes a lot of ressources and the
(1) solution is better, using global variables.

I am going to try to use the (2) solutions, with a module for any files
like:

# inc.test.rb
module Inc
def say
'Hello' + subject
end
end

But is this possible in my case, because I don't know the name of each
module (which is depend of the name of its file)?

Regards
--
Posted via http://www.ruby-....

Joel VanderWerf

2/16/2009 7:45:00 PM

0

Cyril Beer wrote:
> Do you know how loading a Ruby source with parameters? I had try so by
> using:
> load(my_file my_arg)

It's a bit awkward, but there's a way to do it with my script library:

http://redshift.sourceforge.n...

Quoting the docs:
==========
An "input" can be passed to the script before loading. Simply call
Script.new (or Script.load) with a block. The block is passed a single
argument, the Script module, and executed before the files are loaded
into the Scriptâ??s scope. Setting a constant in this block makes the
constant available to the script during loading. For example:
script = Script.load("my-script.rb") { |script| script::INPUT = 3 }
==========

The file "my-script.rb" would simply refer to INPUT. You can pass any
number of args this way. See the "program2.rb" in the examples/ dir for
an example.

As a bonus, everything defined in "my-script.rb" is wrapped in a module,
returned by Script.load, and (in the case above) stored in a local
variable in the main file, which you can use to access the constants and
methods defined in my-script.rb.

HTH.

--
vjoel : Joel VanderWerf : path berkeley edu : 510 665 3407

Brian Candler

2/16/2009 8:27:00 PM

0

Sai Hl wrote:
> I am going to try to use the (2) solutions, with a module for any files
> like:
>
> # inc.test.rb
> module Inc
> def say
> 'Hello' + subject
> end
> end
>
> But is this possible in my case, because I don't know the name of each
> module (which is depend of the name of its file)?

If you are consistent in your naming, you can map the filename to the
module name (or vice versa). For example, look at the underscore and
camelize methods of ActiveSupport from Rails. These just convert FooBar"
to "foo_bar", and vice versa.

Then you can use const_get to convert the name "FooBar" to the actual
module instance on which to invoke the method. e.g.

puts Object.const_get("Inc").say(subject)

A simpler solution is just to iterate over all the modules within an
enclosing module/namespace:

==> inc1.rb <==
module Extensions
module Inc1
def self.say(subject)
"Hello #{subject}"
end
end
end

==> inc2.rb <==
module Extensions
module Inc2
def self.say(subject)
"Goodbye #{subject}"
end
end
end

==> main.rb <==
Dir["inc*.rb"].each { |src| load src }
Extensions.constants.each do |k|
puts Extensions.const_get(k).say("world")
end

Aside: if you strip off the .rb extension (look at File.basename) then
you can use 'require' instead of 'load'. This prevents loading the same
file multiple times.
--
Posted via http://www.ruby-....

Cyril Beer

2/16/2009 11:06:00 PM

0

Thank you, Brian Candler!
Your help was very helpful. You should be a great teacher!

Regards.
--
Posted via http://www.ruby-....

Jeff Schwab

2/17/2009 2:06:00 PM

0

Sai Hl wrote:
> Brian Candler wrote:
>> (1) Loading in more Ruby code to the currently-running Ruby interpreter.
>> This is done using "load" or "require". There is no concept of
>> "parameters" here. However you could set a global variable (e.g. $foo)
>> or a constant (Foo), which the code in the other file makes use of.
>>
>> But it would be more normal for the other file just to define modules or
>> classes, and then after the load has completed you invoke one of those
>> modules or classes, at which point you can pass whatever parameters you
>> like.
>>
>> (2) Forking and execing a new child process. This could be another
>> Ruby interpreter, but it could also be any other program on your system.
>> When you do this, you can pass command-line arguments (and/or
>> environment variables and open files)

> I am going to try to use the (2) solutions

Out of curiosity, why wouldn't you just define a function in the "other"
file, then call it with whatever arguments you want? This is the second
paragraph of (1).