Super super ?

Discussion in 'Ruby' started by Marc-antoine Kruzik, May 19, 2009.

  1. Hello, I'm looking for informations about "super".

    I have 3 classes : grandfather, father, and son.
    And they all have a method named "say_hello".



    Code:
    class Grand_father
    def say_hello
    puts "Grand Father : Hello"
    end
    end
    
    class Father < Grand_father
    def say_hello
    super
    puts "Father : Hello"
    end
    end
    
    class Son < Father
    def say_hello
    super
    puts "Son : Hello"
    end
    end
    
    s = Son.new
    s.say_hello
    Grand Father : Hello
    Father : Hello
    Son : Hello

    But now, I would that Son didn't call Father, but directly Grand_father.

    s.say_hello
    Grand Father : Hello
    Son : Hello

    How could I do that ?
    --
    Posted via http://www.ruby-forum.com/.
     
    Marc-antoine Kruzik, May 19, 2009
    #1
    1. Advertising

  2. Marc-antoine Kruzik

    Ilan Berci Guest

    Marc-antoine Kruzik wrote:

    >
    > But now, I would that Son didn't call Father, but directly Grand_father.
    >
    > s.say_hello
    > Grand Father : Hello
    > Son : Hello
    >
    > How could I do that ?


    I am taking a break at work so I can't test it, but could you please
    try:
    super.super.say_hello
    --
    Posted via http://www.ruby-forum.com/.
     
    Ilan Berci, May 19, 2009
    #2
    1. Advertising

  3. On 19.05.2009 21:29, Marc-antoine Kruzik wrote:
    > Hello, I'm looking for informations about "super".
    >
    > I have 3 classes : grandfather, father, and son.
    > And they all have a method named "say_hello".
    >
    >
    >
    >
    Code:
    > class Grand_father
    >   def say_hello
    >     puts "Grand Father : Hello"
    >   end
    > end
    >
    > class Father < Grand_father
    >   def say_hello
    >     super
    >     puts "Father : Hello"
    >   end
    > end
    >
    > class Son < Father
    >   def say_hello
    >     super
    >     puts "Son : Hello"
    >   end
    > end
    > 
    >
    > s = Son.new
    > s.say_hello
    > Grand Father : Hello
    > Father : Hello
    > Son : Hello
    >
    > But now, I would that Son didn't call Father, but directly Grand_father.
    >
    > s.say_hello
    > Grand Father : Hello
    > Son : Hello
    >
    > How could I do that ?


    You can do

    class Son < Father
    def say_hello
    Grand_father.instance_method:)say_hello).bind(self).call
    puts "Son : Hello"
    end
    end

    However, as the weird construction indicates something might be wrong
    with this kind of design. If you assume that the method actually had
    side effects on the instance's state and you leave out one class in the
    chain you likely end up with an instance in an inconsistent state. In
    that case the design probably needs some work.

    Btw, if Father does not define say_hello super will automatically call
    Grand_father's method.

    Kind regards

    robert

    --
    remember.guy do |as, often| as.you_can - without end
    http://blog.rubybestpractices.com/
     
    Robert Klemme, May 19, 2009
    #3
  4. On 19.05.2009 22:36, Ilan Berci wrote:
    > Marc-antoine Kruzik wrote:
    >
    >> But now, I would that Son didn't call Father, but directly Grand_father.
    >>
    >> s.say_hello
    >> Grand Father : Hello
    >> Son : Hello
    >>
    >> How could I do that ?

    >
    > I am taking a break at work so I can't test it, but could you please
    > try:
    > super.super.say_hello


    This won't work - at least not in the way you intended. :)

    Kind regards

    robert


    --
    remember.guy do |as, often| as.you_can - without end
    http://blog.rubybestpractices.com/
     
    Robert Klemme, May 19, 2009
    #4
  5. Marc-antoine Kruzik

    F. Senault Guest

    Le 19 mai à 21:29, Marc-antoine Kruzik a écrit :

    > Hello, I'm looking for informations about "super".

    /.../
    > I have 3 classes : grandfather, father, and son.
    > And they all have a method named "say_hello".
    > But now, I would that Son didn't call Father, but directly Grand_father.
    >
    > s.say_hello
    > Grand Father : Hello
    > Son : Hello
    >
    > How could I do that ?


    As others said, refactor, there's a problem with you inheritance logic.

    That being said, you could work in the Father class like this to obtain
    the wanted result :


    class Father < Grand_father
    def say_hello
    super
    puts "Father : Hello" unless self.is_a? Son
    end
    end

    Fred
    --
    First, there was the command-line interface. This allowed users to type
    a line of text representing a "command", press the RETURN key, and
    receive a response like "0x38754: ERROR_NOTEXT_PETUNIA". Thanks to this
    handy software tool, the suicide rate rose almost overnight. (D Barrett)
     
    F. Senault, May 20, 2009
    #5
  6. 2009/5/20 F. Senault <>:

    > That being said, you could work in the Father class like this to obtain
    > the wanted result :
    >
    >
    > class Father < Grand_father
    > =A0def say_hello
    > =A0 =A0super
    > =A0 =A0puts "Father : Hello" unless self.is_a? Son
    > =A0end
    > end


    Frankly, I find that even worse than my hack. The reason: now Father
    needs to know something about a sub class so we have a circular
    dependency. That's usually a bad thing to have. Consider, all these
    classes are in different files and someone only needs Father and
    Grand_father: code will break in Father because Son is undefined.
    It's ok if Son knows something about his parents but not otherwise.

    Kind regards

    robert


    --=20
    remember.guy do |as, often| as.you_can - without end
    http://blog.rubybestpractices.com/
     
    Robert Klemme, May 20, 2009
    #6
  7. Marc-antoine Kruzik

    KDr2 Guest

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

    class Object
    def super!(n,*args)
    method=caller[0][%r/.*?`(.*?)'/,1].to_sym
    klass=self.class.ancestors[n]
    klass.instance_method(method).bind(self).call(*args)
    end
    end


    class Grand_father
    def say_hello
    puts "Grand Father : Hello"
    end
    end

    class Father < Grand_father
    def say_hello
    super
    puts "Father : Hello"
    end
    end

    class Son < Father
    def say_hello
    super! 2
    puts "Son : Hello"
    end
    end

    s = Son.new
    s.say_hello


    On Wed, May 20, 2009 at 3:29 AM, Marc-antoine Kruzik
    <>wrote:

    > s = Son.new
    > s.say_hello
    >




    --
    Best Regards,
    -- KDr2, at x-macro.com.
     
    KDr2, May 20, 2009
    #7
  8. Marc-antoine Kruzik

    F. Senault Guest

    Le 20 mai à 10:51, Robert Klemme a écrit :

    > Frankly, I find that even worse than my hack.


    Of course... :)

    Fred
    --
    Au bout De la course Remonte jusqu'a A la source One trip One noise
    Circuit Nuit bleue Spécialiste De l'enjeu One trip One noise
    Longue attente avant de s'elancer One trip (Noir Désir,
    Longue vie et tout a recracher One noise One Trip / One Noise)
     
    F. Senault, May 20, 2009
    #8
  9. Ilan Berci wrote:
    > I am taking a break at work so I can't test it, but could you please
    > try:
    > super.super.say_hello


    Too bad it doesn't work. But it was pretty logical. :)


    @ KDr2

    That is exactly what I needed ! :D
    Thank you very much.
    --
    Posted via http://www.ruby-forum.com/.
     
    Marc-antoine Kruzik, May 20, 2009
    #9
  10. Marc-antoine Kruzik

    Codeblogger Guest

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

    2009/5/20 Marc-antoine Kruzik <>

    >
    > Too bad it doesn't work. But it was pretty logical. :)
    >
    >

    I don't think it was logical, but I guess, that's a matter of taste and
    expectation of what 'super' does.
    And still: KDr2's solution is bad software design.

    Regards
    Nicolai
     
    Codeblogger, May 20, 2009
    #10
  11. Marc-antoine Kruzik

    Ilan Berci Guest

    Robert Klemme wrote:

    >
    > class Son < Father
    > def say_hello
    > Grand_father.instance_method:)say_hello).bind(self).call
    > puts "Son : Hello"
    > end
    > end
    >
    >


    Ahh.. cool! Thanks for the bind() solution, I am aware of it but it
    always falls to the back of my head.. I blame either my age, marriage,
    or kids on this one..

    ilan


    --
    Posted via http://www.ruby-forum.com/.
     
    Ilan Berci, May 20, 2009
    #11
  12. Marc-antoine Kruzik

    Pieter V. Guest

    Depending on your purpose, it may make sense to allow the caller to
    specify which class to invoke the method in. =C2=A0(This won't frequently
    be the case, but since you're specifically looking to invoke your
    Grandfather's method, it might apply here.)

    --------8<-------------------------

    def Grandfather
    =C2=A0=C2=A0def say_hello(klass=3Dself.class)
    return super unless self.is_a?(klass)
    =C2=A0=C2=A0 =C2=A0puts 'Grandfather: Hello'
    =C2=A0=C2=A0end
    end

    def Father < Grandfather
    def say_hello(klass=3Dself.class)
    return super unless self.is_a?(klass)
    puts 'Father: Hello'
    end
    end

    def Son < Father
    def say_hello(klass=3Dself.class)
    return super(Grandfather) unless self.is_a?(klass)
    puts 'Son: Hello'
    end
    end

    --------8<-------------------------

    It's not a best practice, but it might prove useful enough for your case.


    On Wed, May 20, 2009 at 7:46 AM, Ilan Berci <> wrote:
    >
    > Robert Klemme wrote:
    >
    > >
    > > class Son < Father
    > > =C2=A0 =C2=A0def say_hello
    > > =C2=A0 =C2=A0 =C2=A0Grand_father.instance_method:)say_hello).bind(self)=

    call
    > > =C2=A0 =C2=A0 =C2=A0puts "Son : Hello"
    > > =C2=A0 =C2=A0end
    > > end
    > >
    > >

    >
    > Ahh.. cool! Thanks for the bind() solution, I am aware of it but it
    > always falls to the back of my head.. I blame either my age, marriage,
    > or kids on this one..
    >
    > ilan
    >
    >
    > --
    > Posted via http://www.ruby-forum.com/.
    >
     
    Pieter V., May 20, 2009
    #12
  13. Pieter V. wrote:
    > Depending on your purpose, it may make sense to allow the caller to
    > specify which class to invoke the method in.  (This won't frequently
    > be the case, but since you're specifically looking to invoke your
    > Grandfather's method, it might apply here.)
    >
    > It's not a best practice, but it might prove useful enough for your
    > case.


    This was just an example. These methods have sometimes arguments, so I
    had to find something else.

    Because we found by ourselves two solutions, and yours was one of these.
    The other was to use aliases, but it was bad.
    --
    Posted via http://www.ruby-forum.com/.
     
    Marc-antoine Kruzik, May 20, 2009
    #13
    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. Guest

    super.super.super how?

    Guest, Feb 19, 2005, in forum: Java
    Replies:
    24
    Views:
    10,866
    Darryl Pierce
    Feb 24, 2005
  2. Fernando Rodriguez

    Getting the super class via the super() function

    Fernando Rodriguez, Nov 21, 2003, in forum: Python
    Replies:
    2
    Views:
    749
    Bob Willan
    Nov 22, 2003
  3. Kerim Borchaev

    super. could there be a simpler super?

    Kerim Borchaev, Jan 15, 2004, in forum: Python
    Replies:
    4
    Views:
    492
    Michele Simionato
    Jan 15, 2004
  4. Replies:
    7
    Views:
    450
    Patricia Shanahan
    Apr 6, 2008
  5. GOOD LUCK GROUP
    Replies:
    0
    Views:
    415
    GOOD LUCK GROUP
    Apr 28, 2008
Loading...

Share This Page