mixin technique overrides variables

Discussion in 'Ruby' started by Konrad K., Jan 5, 2011.

  1. Konrad K.

    Konrad K. Guest

    Take a look at code bellow:

    module Parent1
    def initialize
    @loc1 = 1
    @loc2 = 2
    end
    end

    class Parent2
    def initialize
    @loc3 = 3
    @loc4 = 4
    end

    def displayp2
    puts @loc3
    puts @loc4
    end
    end

    class Child < Parent2
    include Parent1
    def displayc
    puts @loc1
    puts @loc2
    puts @loc3
    puts @loc4
    end
    end


    c = Child.new
    c.displayc


    I was thinking of something similar to multiple inheritance and my
    expectaions was that all of local variables will be available in Child
    class.
    What I discovered that when you add
    include Parent1
    line to Child class @loc3 and @loc4 disappears.
    When you comment this line @loc3 and @loc4 are available in Child class.

    My question is why this work that way and how to get all of @loc
    available in Child class?

    --
    Posted via http://www.ruby-forum.com/.
     
    Konrad K., Jan 5, 2011
    #1
    1. Advertising

  2. [Note: parts of this message were removed to make it a legal post.]

    It works this way because when you include Parent1, you give its initialize
    method to the Child class, so when you create a new instance of Child, it
    calls Child#initialize, which exists after the include and therefore
    Parent2#initialize in the inheritance chain is never needed. Without the
    include, Child#initialize ends up at Parent2#initialize via inheritance.

    On Wed, Jan 5, 2011 at 12:10 PM, Konrad K. <> wrote:

    > Take a look at code bellow:
    >
    > module Parent1
    > def initialize
    > @loc1 = 1
    > @loc2 = 2
    > end
    > end
    >
    > class Parent2
    > def initialize
    > @loc3 = 3
    > @loc4 = 4
    > end
    >
    > def displayp2
    > puts @loc3
    > puts @loc4
    > end
    > end
    >
    > class Child < Parent2
    > include Parent1
    > def displayc
    > puts @loc1
    > puts @loc2
    > puts @loc3
    > puts @loc4
    > end
    > end
    >
    >
    > c = Child.new
    > c.displayc
    >
    >
    > I was thinking of something similar to multiple inheritance and my
    > expectaions was that all of local variables will be available in Child
    > class.
    > What I discovered that when you add
    > include Parent1
    > line to Child class @loc3 and @loc4 disappears.
    > When you comment this line @loc3 and @loc4 are available in Child class.
    >
    > My question is why this work that way and how to get all of @loc
    > available in Child class?
    >
    > --
    > Posted via http://www.ruby-forum.com/.
    >
    >
     
    Adam Prescott, Jan 5, 2011
    #2
    1. Advertising

  3. Konrad K.

    Josh Cheek Guest

    [Note: parts of this message were removed to make it a legal post.]

    On Wed, Jan 5, 2011 at 6:10 AM, Konrad K. <> wrote:

    > I was thinking of something similar to multiple inheritance and my
    > expectaions was that all of local variables will be available in Child
    > class.
    > What I discovered that when you add
    > include Parent1
    > line to Child class @loc3 and @loc4 disappears.
    > When you comment this line @loc3 and @loc4 are available in Child class.
    >
    > My question is why this work that way and how to get all of @loc
    > available in Child class?
    >
    >

    module Parent1
    def initialize
    @loc1 = 1
    @loc2 = 2
    end
    end

    class Parent2
    def initialize
    @loc3 = 3
    @loc4 = 4
    end

    def displayp2
    puts @loc3
    puts @loc4
    end
    end

    class Child < Parent2
    def displayc
    puts @loc1
    puts @loc2
    puts @loc3
    puts @loc4
    end
    end


    # You can see that when we ask the child for its initialize method,
    # it finds the one that Parent2 has defined, then when we include Parent1,
    # it gets inserted before Parent2 in the inheritance chain,
    # and Child finds the one that Parent1 has defined.
    c = Child.new
    Child.ancestors # => [Child, Parent2, Object, Kernel, BasicObject]
    c.method:)initialize) # => #<Method: Child(Parent2)#initialize>

    class Child
    include Parent1
    end
    Child.ancestors # => [Child, Parent1, Parent2, Object, Kernel,
    BasicObject]
    c.method:)initialize) # => #<Method: Child(Parent1)#initialize>



    # To get all the @loc, you can have the initialize method in Parent1 call
    super,
    # which will find the next one in the chain.
    # note: super will forward any args that the method received,
    # so you don't have to manually pass them on, unless you wish to change them
    Child.new.instance_variables # => [:mad:loc1, :mad:loc2]
    module Parent1
    def initialize
    super
    @loc1 = 1
    @loc2 = 2
    end
    end
    Child.new.instance_variables # => [:mad:loc3, :mad:loc4, :mad:loc1, :mad:loc2]
     
    Josh Cheek, Jan 5, 2011
    #3
  4. Konrad K.

    Konrad K. Guest

    You're right, thanks for explanation ;)

    I decided to rename method in Parent1 from initialize to initializeP and
    define initialize method in Child which calls super and initializeP, now
    everything works fine.

    --
    Posted via http://www.ruby-forum.com/.
     
    Konrad K., Jan 5, 2011
    #4
  5. On Wed, Jan 5, 2011 at 2:27 PM, Konrad K. <> wrote:
    > You're right, thanks for explanation ;)
    >
    > I decided to rename method in Parent1 from initialize to initializeP and
    > define initialize method in Child which calls super and initializeP, now
    > everything works fine.


    IMHO this is a superior approach: define a method initialize for all
    modules with signature (*a,&b) - this will integrate will *every*
    inheritance chain and nicely play with all classes. So you can mix it
    in into several different inheritance hierarchies.

    module Parent1
    def initialize(*a,&b)
    super
    @loc1 = 1
    @loc2 = 2
    end
    end

    module Parent2
    def initialize(*a,&b)
    super
    @loc3 = 3
    @loc4 = 4
    end
    end

    class Child
    include Parent1
    end

    p Child.new.instance_variables

    class Child
    include Parent2
    end

    p Child.new.instance_variables

    class Child
    def initialize
    super
    @loc5 = 5
    end
    end

    p Child.new.instance_variables

    Kind regards

    robert

    --
    remember.guy do |as, often| as.you_can - without end
    http://blog.rubybestpractices.com/
     
    Robert Klemme, Jan 5, 2011
    #5
  6. Konrad K.

    Josh Cheek Guest

    Re: This Email List

    [Note: parts of this message were removed to make it a legal post.]

    On Wed, Jan 5, 2011 at 10:42 AM, <> wrote:

    >
    >
    > I have gone through the process of unsubscribing from this mailing
    > list numerous time to no avail. It is filling up my email box and I want to
    > discontinue receiving emails. The last time I did it, within less than a
    > minute, it told me that my request to get off the mailing list had expired.
    > If the ruby-lang site is written in Ruby, it doesn't give me much confidence
    > that Ruby is right for what I need to do.
    >
    >
    >
    > So...the answer remains..how do I unsubscribe?
    >
    >
    >
    > --Peter




    http://www.ruby-lang.org/en/community/mailing-lists/

    Have you tried that one? There is a giant form at the bottom for
    unsubscribing.
     
    Josh Cheek, Jan 5, 2011
    #6
  7. Re: This Email List

    On Wed, Jan 5, 2011 at 6:01 PM, Josh Cheek <> wrote:
    > On Wed, Jan 5, 2011 at 10:42 AM, <> wrote:
    >
    > http://www.ruby-lang.org/en/community/mailing-lists/
    >
    > Have you tried that one? There is a giant form at the bottom for
    > unsubscribing.


    And as large as the form is, teh "unsubscribe" option can hide itself
    well. It's in the "Action" drop down menu.

    --
    Phillip Gawlowski

    Though the folk I have met,
    (Ah, how soon!) they forget
    When I've moved on to some other place,
    There may be one or two,
    When I've played and passed through,
    Who'll remember my song or my face.
     
    Phillip Gawlowski, Jan 5, 2011
    #7
    1. Advertising

Want to reply to this thread or ask your own question?

It takes just 2 minutes to sign up (and it's free!). Just click the sign up button to choose a username and then you can ask your own questions on the forum.
Similar Threads
  1. Andreas Klemt
    Replies:
    0
    Views:
    483
    Andreas Klemt
    Jul 4, 2003
  2. David Waz...
    Replies:
    0
    Views:
    424
    David Waz...
    Jul 4, 2003
  3. Mac
    Replies:
    1
    Views:
    643
  4. John Lane
    Replies:
    6
    Views:
    210
    John Lane
    Feb 9, 2010
  5. JP Billaud

    Module Mixin & Class Variables

    JP Billaud, Mar 6, 2011, in forum: Ruby
    Replies:
    0
    Views:
    148
    JP Billaud
    Mar 6, 2011
Loading...

Share This Page