[EVALUATION] - E03 - jamLang Evaluation Case Applied to Ruby

Discussion in 'Ruby' started by Ilias Lazaridis, Mar 18, 2005.

  1. [EVALUATION] - E02 - Nitro, a Ruby Based WebFramework
    http://groups-beta.google.com/group/comp.lang.ruby/msg/0fb8b0824d4fbaec

    -

    The above thread showed finally the need to split the evaluation down
    into smaller chunks.

    Here is a simple evaluation template (first part) which can be applied
    to the Ruby language:

    http://lazaridis.com/case/lang/index.html

    If you like, please post the most elegant solutions (either to sections
    or to the whole document).

    I will collect the results and write them down in a document, which will
    compare ruby with other languages.

    This document can serve as an flash-start (for people which simply like
    to take a look on ruby).

    http://lazaridis.com/case/lang/ruby.html

    ..

    --
    http://lazaridis.com
     
    Ilias Lazaridis, Mar 18, 2005
    #1
    1. Advertising

  2. Ilias Lazaridis <> wrote:
    >
    > The above thread showed finally the need to split the evaluation down
    > into smaller chunks.
    >
    > Here is a simple evaluation template (first part) which can be applied
    > to the Ruby language:
    >
    > http://lazaridis.com/case/lang/index.html


    Okay, that's a neat bit of work. Here's a quick solution (ruby makes
    most of this fairly trivial):

    # here's your basic talker class

    class Talker
    def sayHello
    puts "Hello world"
    end
    end

    # __FILE__ == $0 means that the program is being run directly
    # rather than 'require'd from another file

    if __FILE__ == $0
    talker = Talker.new
    talker.sayHello
    end

    # one-pass interpreter, and you can reopen classes
    # so let's just continue

    # here are the two instance variables added to the class, complete with
    # autogenerated getters and setters

    class Talker
    attr_accessor :name, :age

    def initialize(name, age)
    @name, @age = name, age
    end

    # following the spec, though say_name is more rubyish
    def sayYourName
    puts @name
    end

    def sayYourAge
    puts @age
    end
    end

    # now note that our object 'talker' has access to the new methods in its
    # class

    if __FILE__ == $0
    # note that we aren't breaking encapsulation and accessing the vars directly;
    # the setter methods are called name= and age=, and the getters are called
    # name and age
    talker.name = "Just another talker"
    talker.age = 1
    talker.sayYourName
    talker.sayYourAge
    end

    # reflection
    class Talker

    # simple

    def sayYourClassName
    puts self.class.name # the 'self' is optional here
    end

    # objects know nothing about the variables that are bound to them
    # (a variable name is not the name of the instance anyway). The
    # closest you can come to the "name" of an object is it's object id, so...
    def sayYourInstanceName
    puts object_id # again, you could say self.object_id if you prefer
    end

    # advanced

    # caller returns a stack (array) of strings of the form
    # file:linenumber in `method'
    # so we extract the most recent one and parse the method name out
    # code from PLEAC
    def thisMethodName
    caller[0] =~ /in `([^']+)'/ ? $1 : '(anonymous)';
    end

    # string interpolation in action - the bit between the #{} can be
    # any valid expression; to_s will be called on the result and
    # interpolated into the string
    def sayHelloAdvanced
    puts "#{thisMethodName}: Hello World"
    end

    # expert
    def sayYourClassDefinition
    puts "Class:"
    sayYourClassName

    # %{} is another way to write a string literal
    # (looks neat for multiline strings)
    # we use the standard 'inspect' method to print out arrays of
    # method names in a ["meth1", "meth2", ...] format
    puts %{
    Methods:
    public:
    #{public_methods.inspect}
    protected
    #{protected_methods.inspect}
    private:
    #{private_methods.inspect}
    non-inherited:
    #{(methods - self.class.superclass.instance_methods).inspect}

    Instance Variables:
    #{instance_variables.inspect}
    }

    # note that the instance variables belong to the *instance*, not
    # to the class, so they're not technically part of the class
    # definition. the following code is illustrative:
    #
    # class A
    # attr_accessor :foo, :bar # defines getters and setters
    # end
    #
    # a = A.new
    # p a.instance_variables # => []
    # a.foo = 10
    # p a.instance_variables # => ["@foo"]
    # b = A.new
    # p b.instance_variables # => []
    end

    def sayYourClassCode
    puts "Sadly, you cannot introspect the source code from within a program"
    # though see http://rubyforge.org/projects/parsetree/
    # for a way to get at the parsed AST
    end
    end

    # testing it out

    if __FILE__ == $0
    talker.sayHelloAdvanced
    talker.sayYourClassName
    talker.sayYourClassDefinition
    talker.sayYourClassCode
    end

    Hope this helps.

    martin
     
    Martin DeMello, Mar 18, 2005
    #2
    1. Advertising

  3. Martin DeMello wrote:
    > Ilias Lazaridis <> wrote:
    >
    >>The above thread showed finally the need to split the evaluation down
    >>into smaller chunks.
    >>
    >>Here is a simple evaluation template (first part) which can be applied
    >>to the Ruby language:
    >>
    >>http://lazaridis.com/case/lang/index.html

    >
    > Okay, that's a neat bit of work. Here's a quick solution (ruby makes
    > most of this fairly trivial):


    I apologize for the late answer.

    > # here's your basic talker class
    >
    > class Talker
    > def sayHello
    > puts "Hello world"
    > end
    > end


    ok

    > # __FILE__ == $0 means that the program is being run directly
    > # rather than 'require'd from another file
    >
    > if __FILE__ == $0
    > talker = Talker.new
    > talker.sayHello
    > end


    Assuming I placethe code into the file "talker.rb".

    from the command-line, i like to start it, e.g. with "ruby talker.rb"

    I miss a "main" directive / function / object.

    something like:

    def main
    talker = Talker.new
    talker.sayHello
    end

    > # one-pass interpreter, and you can reopen classes
    > # so let's just continue


    [sidenote: I don't understand this]

    > # here are the two instance variables added to the class, complete with
    > # autogenerated getters and setters


    very nice!

    > class Talker
    > attr_accessor :name, :age


    can I write?:

    attr_accessor :name
    attr_accessor :age

    > def initialize(name, age)
    > @name, @age = name, age
    > end


    Is this the constructor?

    I assume I can write

    def initialize(name, age)
    @name = name
    @age = age
    end

    > # following the spec, though say_name is more rubyish
    > def sayYourName
    > puts @name
    > end


    can I write?: def sayYourName puts @name end

    > def sayYourAge
    > puts @age
    > end
    > end


    ok

    > # now note that our object 'talker' has access to the new methods in its
    > # class
    >
    > if __FILE__ == $0
    > # note that we aren't breaking encapsulation and accessing the vars directly;
    > # the setter methods are called name= and age=, and the getters are called
    > # name and age


    very(!) nice!

    > talker.name = "Just another talker"
    > talker.age = 1
    > talker.sayYourName
    > talker.sayYourAge
    > end


    ok

    > # reflection

    [...]

    seperate message will follow.

    ..

    --
    http://lazaridis.com
     
    Ilias Lazaridis, Mar 20, 2005
    #3
  4. On Mon, 21 Mar 2005 02:59:53 +0900, Ilias Lazaridis <> wrote:
    > Martin DeMello wrote:
    > > Ilias Lazaridis <> wrote:
    > >
    > > # __FILE__ == $0 means that the program is being run directly
    > > # rather than 'require'd from another file
    > >
    > > if __FILE__ == $0
    > > talker = Talker.new
    > > talker.sayHello
    > > end

    >
    > Assuming I placethe code into the file "talker.rb".
    >
    > from the command-line, i like to start it, e.g. with "ruby talker.rb"
    >
    > I miss a "main" directive / function / object.


    You can think of the whole file as "main". The code will be read from
    top to bottom.

    > > # one-pass interpreter, and you can reopen classes
    > > # so let's just continue

    >
    > [sidenote: I don't understand this]


    Example:

    # first time setting the class
    class Talker
    attr_accessor :name

    def initialize(name)
    @name = name
    end

    end

    talker = Talker.new('Bob')
    puts talker.name

    # reopen the class to add sayYourName
    class Talker
    def sayYourName
    puts @name
    end
    end

    talker.sayYourName


    The output is:

    Bob
    Bob


    > > class Talker
    > > attr_accessor :name, :age

    >
    > can I write?:
    >
    > attr_accessor :name
    > attr_accessor :age


    yes

    > > def initialize(name, age)
    > > @name, @age = name, age
    > > end

    >
    > Is this the constructor?
    >
    > I assume I can write
    >
    > def initialize(name, age)
    > @name = name
    > @age = age
    > end


    yes

    > > # following the spec, though say_name is more rubyish
    > > def sayYourName
    > > puts @name
    > > end

    >
    > can I write?: def sayYourName puts @name end


    You need to add semicolons if you want to put more than one line on a line:

    def sayYourName; puts @name; end

    hth,
    Douglas
     
    Douglas Livingstone, Mar 21, 2005
    #4
  5. Ilias Lazaridis <> wrote:
    >
    > > # one-pass interpreter, and you can reopen classes
    > > # so let's just continue

    >
    > [sidenote: I don't understand this]


    The ruby interpreter is one-pass insofar as it takes a single pass through
    the file, from top to bottom, building and executing an abstract syntax tree
    as it goes. Anything enclosed in a def...end block (and a few other
    delayed-evaluation constructs like lambda) gets converted into a 'callable'
    block of code, the rest is just executed. That's how attr_accessor works,
    incidentally - it's just a piece of code that runs inside a class's context
    and generates methods when it's executed. Try the following:

    class Foo
    def say_hello
    puts "hello world"
    end

    puts "hi, this is the reader"
    end

    a = Foo.new
    a.say_hello

    the first puts statement gets executed when say_hello is called; the second
    one is not inside a def statement, and so gets executed when the interpreter
    gets to it.

    Hence the lack of a main() method - in a sense, the whole fine is a main(),
    since the entry point is the top of the file (comes in real handy when
    writing quick imperative scripts - you aren't forced to define a class just
    because Ruby is a pure OO language).

    Hence the if __FILE__ == $0 blocks - if the file is not being run directly,
    the condition fails, and the whole block is skipped.

    As for reopening classes, you can modify a class at runtime (add/delete
    methods, mix in a module), and any objects belonging to the class inherit
    those modifications (rather trivially, since they look up methods in the
    class). But, since this is a one pass interpreter, those changes come into
    effect at the time the reader reads them, and so the object "changes" in the
    middle of its lifecycle.

    martin
     
    Martin DeMello, Mar 21, 2005
    #5
  6. Douglas Livingstone wrote:
    > On Mon, 21 Mar 2005 02:59:53 +0900, Ilias Lazaridis <> wrote:
    >
    >>Martin DeMello wrote:
    >>
    >>>Ilias Lazaridis <> wrote:
    >>>
    >>># __FILE__ == $0 means that the program is being run directly
    >>># rather than 'require'd from another file
    >>>
    >>>if __FILE__ == $0
    >>> talker = Talker.new
    >>> talker.sayHello
    >>>end

    >>
    >>Assuming I placethe code into the file "talker.rb".
    >>
    >>from the command-line, i like to start it, e.g. with "ruby talker.rb"
    >>
    >>I miss a "main" directive / function / object.

    >
    > You can think of the whole file as "main". The code will be read from
    > top to bottom.


    I understand.

    This means that ruby is _not_ strictly Object Oriented.

    And this means that I can drop the "if __FILE__ [...]" construct.

    I like both points.

    -

    I assume I can launch my application with "ruby talker.rb".

    >>># one-pass interpreter, and you can reopen classes
    >>># so let's just continue

    >>
    >>[sidenote: I don't understand this]

    >
    > Example:
    >
    > # first time setting the class
    > class Talker
    > attr_accessor :name
    >
    > def initialize(name)
    > @name = name
    > end
    >
    > end
    >
    > talker = Talker.new('Bob')
    > puts talker.name
    >
    > # reopen the class to add sayYourName
    > class Talker
    > def sayYourName
    > puts @name
    > end
    > end
    >
    > talker.sayYourName
    >
    >
    > The output is:
    >
    > Bob
    > Bob


    [I think I understand, but will postpone this construct]

    >>>class Talker
    >>> attr_accessor :name, :age

    >>
    >>can I write?:
    >>
    >>attr_accessor :name
    >>attr_accessor :age

    >
    > yes


    ok

    >>> def initialize(name, age)
    >>> @name, @age = name, age
    >>> end

    >>
    >>Is this the constructor?
    >>
    >>I assume I can write
    >>
    >> def initialize(name, age)
    >> @name = name
    >> @age = age
    >> end

    >
    > yes


    ok

    >>> # following the spec, though say_name is more rubyish
    >>> def sayYourName
    >>> puts @name
    >>> end

    >>
    >>can I write?: def sayYourName puts @name end

    >
    > You need to add semicolons if you want to put more than one line on a line:
    >
    > def sayYourName; puts @name; end


    ok

    > hth,
    > Douglas


    ..

    --
    http://lazaridis.com
     
    Ilias Lazaridis, Mar 21, 2005
    #6
  7. Martin DeMello wrote:
    > Ilias Lazaridis <> wrote:
    >
    >>># one-pass interpreter, and you can reopen classes
    >>># so let's just continue

    >>
    >>[sidenote: I don't understand this]

    >
    > The ruby interpreter is one-pass insofar as it takes a single pass through

    [...] - (interpreter, dynamic mixins, ...)

    Thank you for you explanations.

    I've understood now everything.

    Altough I'm excited about some contructs, I must postpone their discussion.

    I'll come back to them soon.

    ..

    --
    http://lazaridis.com
     
    Ilias Lazaridis, Mar 21, 2005
    #7
  8. >> You can think of the whole file as "main". The code will be read from
    >> top to bottom.

    [...]
    > This means that ruby is _not_ strictly Object Oriented.


    Ruby is not strictly OO, but not for the reason you think. Here is a
    nice explenation why:
    http://www.rubycentral.com/book/classes.html#S3

    > And this means that I can drop the "if __FILE__ [...]" construct.


    __FILE__ is the name of the current source file.
    $0 is the name of the top-level ruby program being executed.

    So this construct just checks if this the source file is the file that
    is executed directly with e.g. 'ruby talker.rb', and only if this is the
    case, the codeblock will be executed.


    martinus
     
    Martin Ankerl, Mar 21, 2005
    #8
  9. Martin Ankerl wrote:
    >>> You can think of the whole file as "main". The code will be read from
    >>> top to bottom.

    > [...]
    >
    >> This means that ruby is _not_ strictly Object Oriented.

    >
    > Ruby is not strictly OO, but not for the reason you think. Here is a
    > nice explenation why:
    > http://www.rubycentral.com/book/classes.html#S3


    impressive.

    >> And this means that I can drop the "if __FILE__ [...]" construct.

    >
    > __FILE__ is the name of the current source file.


    ok, here i guessed right (intuitive naming).

    > $0 is the name of the top-level ruby program being executed.


    here i thought that "$0" represents "NULL".

    $0 => main-file (or entry-file, or top-level file, or top-level program)

    > So this construct just checks if this the source file is the file that
    > is executed directly with e.g. 'ruby talker.rb', and only if this is the
    > case, the codeblock will be executed.


    Ok, now it's clear.

    > martinus


    ..

    --
    http://lazaridis.com
     
    Ilias Lazaridis, Mar 21, 2005
    #9
  10. Ilias Lazaridis wrote:
    > [EVALUATION] - E02 - Nitro, a Ruby Based WebFramework
    > http://groups-beta.google.com/group/comp.lang.ruby/msg/0fb8b0824d4fbaec
    >
    > -
    >
    > The above thread showed finally the need to split the evaluation down
    > into smaller chunks.
    >
    > Here is a simple evaluation template (first part) which can be applied
    > to the Ruby language:
    >
    > http://lazaridis.com/case/lang/index.html
    >
    > If you like, please post the most elegant solutions (either to sections
    > or to the whole document).
    >
    > I will collect the results and write them down in a document, which will
    > compare ruby with other languages.
    >
    > This document can serve as an flash-start (for people which simply like
    > to take a look on ruby).
    >
    > http://lazaridis.com/case/lang/ruby.html


    The first result is available.

    I would like to setup ruby at this point, to add the installation steps
    to the document.

    Can one suggest me the simplest possible installation (one-click)?

    One for Windows and one for Linux (if possible similar in content)?

    ..

    --
    http://lazaridis.com
     
    Ilias Lazaridis, Mar 23, 2005
    #10
  11. Ilias Lazaridis

    Tom Copeland Guest

    Tom Copeland, Mar 23, 2005
    #11
  12. Martin DeMello wrote:
    > Ilias Lazaridis <> wrote:
    >
    >>The above thread showed finally the need to split the evaluation down
    >>into smaller chunks.
    >>
    >>Here is a simple evaluation template (first part) which can be applied
    >>to the Ruby language:
    >>
    >>http://lazaridis.com/case/lang/index.html

    >
    > Okay, that's a neat bit of work. Here's a quick solution (ruby makes
    > most of this fairly trivial):
    >
    > # here's your basic talker class
    >
    > class Talker
    > def sayHello
    > puts "Hello world"
    > end
    > end


    I will make a slight addition:

    The application main code will be alternatively entered in a seperate
    file, main.rb:

    > talker = Talker.new
    > talker.sayHello


    How does "main.rb" gets knowledge about "talker.rb" ?

    -

    [...]
    > # string interpolation in action - the bit between the #{} can be
    > # any valid expression; to_s will be called on the result and
    > # interpolated into the string
    > def sayHelloAdvanced
    > puts "#{thisMethodName}: Hello World"
    > end

    [...]

    "#" is used as a comment marker _and_ partly within code.

    Can I use another comment marker?

    Can I write "puts "#{thisMethodName}: Hello World"" in an different
    manner, without the use of "#"?

    ..

    --
    http://lazaridis.com
     
    Ilias Lazaridis, Mar 24, 2005
    #12
  13. Ilias Lazaridis

    Jacob Fugal Guest

    On Thu, 24 Mar 2005 10:59:50 +0900, Ilias Lazaridis <> wrote:
    > Martin DeMello wrote:
    > > # here's your basic talker class
    > >
    > > class Talker
    > > def sayHello
    > > puts "Hello world"
    > > end
    > > end

    >
    > I will make a slight addition:
    >
    > The application main code will be alternatively entered in a seperate
    > file, main.rb:
    >
    > > talker = Talker.new
    > > talker.sayHello

    >
    > How does "main.rb" gets knowledge about "talker.rb" ?


    Put the code for the Talker class in a separate file then 'require'
    that file in main.rb. For example, if the Talker class were in
    talker.rb then I'd have:

    require 'talker'

    talker = Talker.new
    talker.sayHello

    for my main.rb. Note that the require statement does not need the .rb
    suffix on the file containing the class.


    > > # string interpolation in action - the bit between the #{} can be
    > > # any valid expression; to_s will be called on the result and
    > > # interpolated into the string
    > > def sayHelloAdvanced
    > > puts "#{thisMethodName}: Hello World"
    > > end

    >
    > "#" is used as a comment marker _and_ partly within code.
    >
    > Can I use another comment marker?


    No. To my knowledge there is only the one comment syntax in ruby.

    > Can I write "puts "#{thisMethodName}: Hello World"" in an different
    > manner, without the use of "#"?


    Sure. #{thisMethodName} in a string literal simply calls .to_s on the
    enclosed expression and inserts it at the designated location. So we
    can pull that out such:

    puts thisMethodName.to_s + ": Hello World"

    The + operator performs concatenation when its arguments are strings.

    Jacob Fugal
     
    Jacob Fugal, Mar 24, 2005
    #13
  14. >>Can I use another comment marker?
    > No. To my knowledge there is only the one comment syntax in ruby.


    You can use e.g.

    =begin
    bla bla
    bla
    =end


    martinus
     
    Martin Ankerl, Mar 24, 2005
    #14
  15. On Mar 24, 2005, at 12:19 PM, Jacob Fugal wrote:

    >> "#" is used as a comment marker _and_ partly within code.
    >>
    >> Can I use another comment marker?

    >
    > No. To my knowledge there is only the one comment syntax in ruby.


    Ruby has a multiline comment syntax:

    =begin
    This is a comment.
    =end

    Just FYI.

    James Edward Gray II
     
    James Edward Gray II, Mar 24, 2005
    #15
  16. Martin DeMello wrote:
    > Ilias Lazaridis <> wrote:
    >
    >>The above thread showed finally the need to split the evaluation down
    >>into smaller chunks.
    >>
    >>Here is a simple evaluation template (first part) which can be applied
    >>to the Ruby language:
    >>
    >>http://lazaridis.com/case/lang/index.html

    >
    > Okay, that's a neat bit of work. Here's a quick solution (ruby makes
    > most of this fairly trivial):
    >
    > # here's your basic talker class

    [...]

    preliminary draft:

    http://lazaridis.com/case/lang/ruby.html

    > # reflection
    > class Talker
    >
    > # simple
    >
    > def sayYourClassName
    > puts self.class.name # the 'self' is optional here
    > end


    omitting "self" (puts class.name) leads to an error

    > # objects know nothing about the variables that are bound to them
    > # (a variable name is not the name of the instance anyway). The
    > # closest you can come to the "name" of an object is it's object id, so...
    > def sayYourInstanceName
    > puts object_id # again, you could say self.object_id if you prefer
    > end


    ok

    > # advanced
    >
    > # caller returns a stack (array) of strings of the form
    > # file:linenumber in `method'
    > # so we extract the most recent one and parse the method name out
    > # code from PLEAC
    > def thisMethodName
    > caller[0] =~ /in `([^']+)'/ ? $1 : '(anonymous)';
    > end


    I understand the concept.

    is there possibly a more direct solution available, with cleaner code
    and a stable/higher execution speed?

    > # string interpolation in action - the bit between the #{} can be
    > # any valid expression; to_s will be called on the result and
    > # interpolated into the string
    > def sayHelloAdvanced
    > puts "#{thisMethodName}: Hello World"
    > end


    ok

    > # expert
    > def sayYourClassDefinition
    > puts "Class:"
    > sayYourClassName


    puts "Class #{self.class.name}" >> Class Talker

    but

    puts "Class #{sayYourClassName}" >> Talker Class
    puts "Class " + sayYourClassName.to_s >> Talker Class

    why?

    > # %{} is another way to write a string literal


    #{} - inside strings
    %{} - outside of strings

    > # (looks neat for multiline strings)
    > # we use the standard 'inspect' method to print out arrays of
    > # method names in a ["meth1", "meth2", ...] format
    > puts %{
    > Methods:
    > public:
    > #{public_methods.inspect}
    > protected
    > #{protected_methods.inspect}
    > private:
    > #{private_methods.inspect}
    > non-inherited:
    > #{(methods - self.class.superclass.instance_methods).inspect}
    >
    > Instance Variables:
    > #{instance_variables.inspect}
    > }


    Can I get somehow a more precise reflection of the class definition
    (output similar to the original class-def, excluding code)?

    > # note that the instance variables belong to the *instance*, not
    > # to the class, so they're not technically part of the class
    > # definition. the following code is illustrative:
    > #
    > # class A
    > # attr_accessor :foo, :bar # defines getters and setters
    > # end
    > #
    > # a = A.new
    > # p a.instance_variables # => []
    > # a.foo = 10
    > # p a.instance_variables # => ["@foo"]
    > # b = A.new
    > # p b.instance_variables # => []
    > end


    ok

    > def sayYourClassCode
    > puts "Sadly, you cannot introspect the source code from within a program"
    > # though see http://rubyforge.org/projects/parsetree/
    > # for a way to get at the parsed AST
    > end


    ok

    > end
    >
    > # testing it out
    >
    > if __FILE__ == $0
    > talker.sayHelloAdvanced
    > talker.sayYourClassName
    > talker.sayYourClassDefinition
    > talker.sayYourClassCode
    > end
    >
    > Hope this helps.


    very much!

    thank you for your efforts.

    > martin


    ..

    --
    http://lazaridis.com
     
    Ilias Lazaridis, Mar 25, 2005
    #16
  17. [from an answer which showed up as a seperate thread]

    James Edward Gray II wrote:
    > Begin forwarded message:
    >
    >>> # reflection
    >>> class Talker
    >>> # simple
    >>> def sayYourClassName
    >>> puts self.class.name # the 'self' is optional here
    >>> end

    >>
    >> omitting "self" (puts class.name) leads to an error

    >
    > I checked this one myself, because it surprised me when you said it.
    > You're right of course. I'm assuming it's because class is a method
    > name and a Ruby keyword.


    ok

    >>> # advanced
    >>> # caller returns a stack (array) of strings of the form #
    >>> file:linenumber in `method'
    >>> # so we extract the most recent one and parse the method name out
    >>> # code from PLEAC
    >>> def thisMethodName
    >>> caller[0] =~ /in `([^']+)'/ ? $1 : '(anonymous)';
    >>> end

    >>
    >> I understand the concept.
    >>
    >> is there possibly a more direct solution available, with cleaner code
    >> and a stable/higher execution speed?

    >
    > Have you measured it and proven it too slow? Remember, premature
    > optimization is the root of all evil in programming. ;)
    >
    > I'm not sure what you consider "clean", but getting rid of the ternary
    > operator may make it a little more readable:
    >
    > if caller[0] =~ /in `([^']+)'/ then $1 else '(anonymous)' end


    I meant something direct like:

    caller.active_method

    >>> # expert
    >>> def sayYourClassDefinition
    >>> puts "Class:"
    >>> sayYourClassName

    >>
    >> puts "Class #{self.class.name}" >> Class Talker
    >>
    >> but
    >>
    >> puts "Class #{sayYourClassName}" >> Talker Class
    >> puts "Class " + sayYourClassName.to_s >> Talker Class
    >>
    >> why?

    >
    > In the first example, you're asking Ruby for the class name, which you
    > add to a string that gets printed by the local call to puts. In the
    > other two, you're calling a method that prints the class name
    > immediately.


    Of course [I've overseen the print statements].

    > Then the local puts prints "Class " and the return value
    > from the method call, which isn't meaningful in this context.


    ok

    >>> # %{} is another way to write a string literal

    >>
    >> #{} - inside strings
    >> %{} - outside of strings

    >
    > No, these are not equivalent. #{...} is for interpolating Ruby code
    > inside a string. %{...} defined a double quoted string, without the
    > quotes:
    >
    > %{This is a string. I can use "quotes" in here. And #{"interpolate"}
    > values.}


    ok, now I understand.

    %{} => string
    #{} => string interpolation of code

    >>> # (looks neat for multiline strings)

    [...]
    >>> }

    >>
    >> Can I get somehow a more precise reflection of the class definition
    >> (output similar to the original class-def, excluding code)?

    >
    > I don't believe so, no. Remember that a Ruby class can be reopened
    > and definitions added to it. That means a class could be built up
    > from many places.
    >
    > Ruby does have a means to get it to store the source code it reads,
    > but I don't believe that's what you were asking for.


    you're right.

    -

    I will try to work this out myself.

    Where can I find the following information?:

    * An UML diagramm (or another visual representation) of the ruby
    class-model.

    * A deep (but compact) description of the reflection/introspection api's.

    > James Edward Gray II


    ..

    --
    http://lazaridis.com
     
    Ilias Lazaridis, Mar 26, 2005
    #17
  18. Ilias Lazaridis wrote:

    > Where can I find the following information?:
    >
    > * An UML diagramm (or another visual representation) of the ruby
    > class-model.


    I've generated this one automatically:

    http://flgr.0x42.net/class-graph.png

    Note that it is quite large and not too pretty, though.

    > * A deep (but compact) description of the reflection/introspection api's.


    Well, the Pickaxe book (slightly outdated version is available online
    for free, new issue with lots of new material can be ordered online)
    contains that among much other information and is a pretty interesting
    read. See

    http://www.rubycentral.com/book/ (first issue)
    http://phrogz.net/ProgrammingRuby/ (first issue with Wiki for changes)
    http://www.pragmaticprogrammer.com/titles/ruby/index.html (second issue)
    http://www.amazon.com/exec/obidos/tg/detail/-/0974514055/ (second issue)

    I'd recommend ordering the second issue from the pragmatic guys as it
    contains detailed information that will be useful for evaluating Ruby in
    depth.
     
    Florian Gross, Mar 26, 2005
    #18
  19. Florian Gross wrote:
    > Ilias Lazaridis wrote:
    >
    >> Where can I find the following information?:
    >>
    >> * An UML diagramm (or another visual representation) of the ruby
    >> class-model.

    >
    > I've generated this one automatically:
    >
    > http://flgr.0x42.net/class-graph.png


    with which tool have you generated this?

    > Note that it is quite large and not too pretty, though.


    This is a nice overview.

    Does anyone has the detailed model of the core class-model?

    >> * A deep (but compact) description of the reflection/introspection
    >> api's.

    >
    > Well, the Pickaxe book (slightly outdated version is available online
    > for free, new issue with lots of new material can be ordered online)
    > contains that among much other information and is a pretty interesting
    > read. See
    >
    > http://www.rubycentral.com/book/ (first issue)
    > http://phrogz.net/ProgrammingRuby/ (first issue with Wiki for changes)
    > http://www.pragmaticprogrammer.com/titles/ruby/index.html (second issue)
    > http://www.amazon.com/exec/obidos/tg/detail/-/0974514055/ (second issue)
    >
    > I'd recommend ordering the second issue from the pragmatic guys as it
    > contains detailed information that will be useful for evaluating Ruby in
    > depth.


    thank you for the information.

    I need at this point only reference of the reflection/introspection api.

    I cannot locate it.

    ..

    --
    http://lazaridis.com
     
    Ilias Lazaridis, Mar 26, 2005
    #19
  20. Ilias Lazaridis wrote:

    >> I've generated this one automatically:
    >>
    >> http://flgr.0x42.net/class-graph.png

    >
    > with which tool have you generated this?


    Graphviz and a custom Ruby script which uses Ruby's introspection for
    finding out the class and module relationships.
     
    Florian Gross, Mar 28, 2005
    #20
    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. Steve Franks
    Replies:
    2
    Views:
    1,282
    Steve Franks
    Jun 10, 2004
  2. Ilias Lazaridis
    Replies:
    2
    Views:
    407
    Ilias Lazaridis
    Apr 24, 2005
  3. Ilias Lazaridis
    Replies:
    18
    Views:
    363
    Bill Guindon
    Apr 9, 2005
  4. Chris Pearl
    Replies:
    0
    Views:
    133
    Chris Pearl
    Oct 16, 2006
  5. Ilias Lazaridis
    Replies:
    2
    Views:
    147
    Ilias Lazaridis
    Apr 24, 2005
Loading...

Share This Page