Include into class after instance is created

Hello,

it’s me again with another question. I want to include a module only after
having instantiated a class. Something like this

File: german.rb
Module Index
Title = 'Meine Seite’
end

File: english.rb
Module Index
Title = 'My Page’
end

file index.rb:
class Index < Website
def initialize
super
include(Index)
end
end

where Website requires either german.rb or english.rb.

But I can’t call include as a function. Ruby complains that it is a
private function of class.

…/index.rb:10:in initialize': private methodinclude’ called for Index:Class (NoMethodError)
from ./index.rb:27:in `new’
from ./index.rb:27

Is this scheme possible, am I totally on the wrong track or just missing
something obvious?

Regards,

Brian

···


Brian Schröder
http://www.brian-schroeder.de/

Use Object#extend instead of include.

Cheers,
Kent.

···

On May 20, 2004, at 9:48 AM, Brian Schroeder wrote:

Hello,

it’s me again with another question. I want to include a module only
after
having instantiated a class. Something like this

File: german.rb
Module Index
Title = ‘Meine Seite’
end

File: english.rb
Module Index
Title = ‘My Page’
end

file index.rb:
class Index < Website
def initialize
super
include(Index)
end
end

where Website requires either german.rb or english.rb.

But I can’t call include as a function. Ruby complains that it is a
private function of class.

…/index.rb:10:in initialize': private method include’ called for
Index:Class (NoMethodError)
from ./index.rb:27:in `new’
from ./index.rb:27

Is this scheme possible, am I totally on the wrong track or just
missing
something obvious?

Regards,

Brian


Brian Schröder
http://www.brian-schroeder.de/

Thanks for the tip.

I need the constants defined in the module to be included in my class, it
seems that extend only includes the instance methods.

$ ri extend
---------------------------------------------------------- Object#extend
obj.extend(module, …) => obj

···

On Thu, 20 May 2004 23:05:10 +0900, Kent S. wrote:

Use Object#extend instead of include.


 Adds to _obj_ the instance methods from each module given as a
 parameter.

Any thoughts about this?

Regards,

Brian


Brian Schröder
http://www.brian-schroeder.de/

How about this:

$ irb
irb(main):001:0> module M1
irb(main):002:1> Const = 1
irb(main):003:1> end
=> 1
irb(main):004:0> module M2
irb(main):005:1> Const = 2
irb(main):006:1> end
=> 2
irb(main):007:0> class A
irb(main):008:1> def initialize(mod)
irb(main):009:2> self.class.class_eval{ include mod }
irb(main):010:2> end
irb(main):011:1>
irb(main):012:1*
irb(main):013:1* def const
irb(main):014:2> puts Const
irb(main):015:2> end
irb(main):016:1> end
=> nil
irb(main):017:0> A.new(M1).const
1
=> nil
irb(main):018:0> A.new(M2).const
2
=> nil
irb(main):019:0>

Cheers,
Kent.

···

On May 20, 2004, at 10:33 AM, Brian Schroeder wrote:

On Thu, 20 May 2004 23:05:10 +0900, Kent S. wrote:

Use Object#extend instead of include.

Thanks for the tip.

I need the constants defined in the module to be included in my class,
it
seems that extend only includes the instance methods.

$ ri extend

Object#extend
obj.extend(module, …) => obj

  • Adds to obj the instance methods from each module given as a
    parameter.

Any thoughts about this?

Regards,

Brian


Brian Schröder
http://www.brian-schroeder.de/

Hi

Brian Schroeder wrote:

I need the constants defined in the module to be included in my class, it
seems that extend only includes the instance methods.

That’s the default behaviour of extend. If you wanted to do extra things
when a module extends an object, you can define a custom “extended”
module method. This is a hook that is run every time an object’s
extended with that module.

For example, to do what you want to do:

···

class Foo
end

module Qux
MY_CONSTANT = ‘HEADACHE’
def Qux.extended(obj)
constants.each do | const |
obj.class.class_eval { const_set(const, Qux.const_get(const))}
end
end
end

f = Foo.new()
f.extend(Qux)

p Foo::MY_CONSTANT # → ‘HEADACHE’

Note that this means that actions upon an instance will affect the
global definition of that instance’s class, which may or may not be what
you want.

You might also be interested in the ‘included’ and ‘append_features’
methods of Module. IIRC, ‘extended’ and ‘included’ were added in Ruby 1.8.0.

cheers
alex