Forum: Ruby Dynamic class change?

Announcement (2017-05-07): www.ruby-forum.com is now read-only since I unfortunately do not have the time to support and maintain the forum any more. Please see rubyonrails.org/community and ruby-lang.org/en/community for other Rails- und Ruby-related community platforms.
Mark N. (Guest)
on 2006-06-11 06:42
(Received via mailing list)
I have a stream I'm listening to that lots of similar things speak on,
each of which also identifies itself with a unique MAC.
Say, I have 3 objects organized something like this:
Class Nic
End

Class Nic2 < Nic
Etc.
End

Class Nic3 < Nic2
Etc.
End

As time passes, when I hear a new MAC start talking, I dynamically
create a corresponding object. So, if the first thing I hear is
something a Nic says, a Nic object can spring into existence, ditto for
Nic2, etc. So far, seems reasonable.

However, the similar things will sometimes appear as a Nic, then say
something new and exciting that indicates that they are actually Nic2
objects (or Nic3, for example).

The simple/crude solution is just to have one nic object with a '@type'
class variable that can get changed once new information appears. Also
the @type variable could be queried to figure out what the object
is/does.

But this just doesn't seem like the ruby way. Is there something obvious
I should be doing that is sensible and cleaner?

The objective is for the calling routine, over time, to know what type
of objects it is talking to (and to efficiently collect the various
types to perform operations on).

Thanks,
Mark
Dave B. (Guest)
on 2006-06-11 08:07
(Received via mailing list)
Mark N. wrote:
> Etc.
> End
>
> As time passes, when I hear a new MAC start talking, I dynamically create a 
corresponding object. So, if the first thing I hear is something a Nic says, a Nic object 
can spring into existence, ditto for Nic2, etc. So far, seems reasonable.
>
> However, the similar things will sometimes appear as a Nic, then say something new and 
exciting that indicates that they are actually Nic2 objects (or Nic3, for example).
>
> The simple/crude solution is just to have one nic object with a '@type' class variable 
that can get changed once new information appears. Also the @type variable could be 
queried to figure out what the object is/does.
>
> But this just doesn't seem like the ruby way. Is there something obvious I should be 
doing that is sensible and cleaner?

You can deal with this by adding a copy constructor, at least to the
subclasses (but it can be inherited).

class Nic
  def initialize(nic = nil)
    if nic
      self.property = nic.property
      #...
    end
  end
end

class Nic2 < Nic
end

nic = Nic.new
nic = Nic2.new(nic)

Cheers,
Dave
unknown (Guest)
on 2006-06-11 08:08
(Received via mailing list)
On Sun, 11 Jun 2006, Mark N. wrote:

> Etc.
>
>
> Thanks,
> Mark

google 'pimpl' : public interface private implimentation.  a simple ruby
version illustrating what you are talking about might look like this:

     harp:~ > cat a.rb
     class Nic
       def initialize
         @impl = NicImpl.new self
       end
       DELEGATE_METHODS = %w(
         a_method
         another_method
       )
       DELEGATE_METHODS.each do |m|
         module_eval " def #{ m }(*a, &b) @impl.#{ m }(*a, &b) end "
       end
       def hear_something_and_become_nic2
         @impl = NicImpl2.new self
       end
       def hear_something_and_become_nic3
         @impl = NicImpl3.new self
       end
     end
     class NicImpl
       def initialize nic
         @nic = nic
       end
       def a_method
         'all nics have this'
       end
     end
     class NicImpl2 < NicImpl
       def another_method
         'this is a nic2'
       end
     end
     class NicImpl3 < NicImpl
       def another_method
         'this is a nic3'
       end
     end

     nic = Nic.new
     p nic.a_method

     nic.hear_something_and_become_nic2
     p nic.another_method

     nic.hear_something_and_become_nic3
     p nic.another_method



     harp:~ > ruby a.rb
     "all nics have this"
     "this is a nic2"
     "this is a nic3"


regards.

-a
Joel VanderWerf (Guest)
on 2006-06-12 01:03
(Received via mailing list)
Mark N. wrote:
> As time passes, when I hear a new MAC start talking, I dynamically
> create a corresponding object. So, if the first thing I hear is
> something a Nic says, a Nic object can spring into existence, ditto
> for Nic2, etc. So far, seems reasonable.
>
> However, the similar things will sometimes appear as a Nic, then say
> something new and exciting that indicates that they are actually Nic2
> objects (or Nic3, for example).

It sounds like you could get away with something like htis:

class Nic
  attr_accessor :mac
end

module Nic2
  def do_nic2_stuff
    puts "nic2 at #{mac}!"
  end
end

module Nic3
end

# when you first hear it
nic = Nic.new
nic.mac = "12:23..."

# later when you have more info
nic.extend Nic2
nic.do_nic2_stuff   # ==> nic2 at 12:23...!


This will work as long as the information you get about these objects is
_monotone_: you never have to back out of extending a nic instance with
modules.
This topic is locked and can not be replied to.