evaluation order

Discussion in 'Ruby' started by Zehao, Feb 13, 2005.

  1. Zehao

    Zehao Guest

    One interesting thing is when running the following codes

    File.open("testfile") |aFile| do
    print a while a=aFile.gets
    end

    one will get an error indicating a doesn't exist. This error can be
    fixed by adding a line a="" before the print command.

    But logically speaking, "print a" should be interpreted after
    "a=File.gets". Is this because the interpreter couldn't find the object
    "a" when first scanning the second line?
    Zehao, Feb 13, 2005
    #1
    1. Advertising

  2. (In response to news:
    by Zehao)

    > File.open("testfile") |aFile| do
    > print a while a=aFile.gets
    > end
    >


    Isn't that File.open('testfile') do |aFile| ?

    k
    Kaspar Schiess, Feb 13, 2005
    #2
    1. Advertising

  3. "Zehao" <> schrieb im Newsbeitrag
    news:...
    > One interesting thing is when running the following codes
    >
    > File.open("testfile") |aFile| do
    > print a while a=aFile.gets
    > end
    >
    > one will get an error indicating a doesn't exist. This error can be
    > fixed by adding a line a="" before the print command.
    >
    > But logically speaking, "print a" should be interpreted after
    > "a=File.gets". Is this because the interpreter couldn't find the object
    > "a" when first scanning the second line?


    I suspect it's the same issue as with local variables: Ruby applies a
    certain heuristic to determine whether something is a local var or not.
    This heuristic is based on *syntactical* order of occurrence

    >> def foo
    >> print a
    >> a = 10
    >> end

    => nil
    >> foo

    NameError: undefined local variable or method `a' for main:Object
    from (irb):2:in `foo'
    from (irb):5

    See also
    http://www.ruby-doc.org/docs/ProgrammingRuby/html/language.html#UO
    http://www.ruby-doc.org/docs/ProgrammingRuby/html/tut_expressions.html#S3

    Kind regards

    robert
    Robert Klemme, Feb 13, 2005
    #3
  4. Hi --

    On Sun, 13 Feb 2005, Robert Klemme wrote:

    >
    > "Zehao" <> schrieb im Newsbeitrag
    > news:...
    >> One interesting thing is when running the following codes
    >>
    >> File.open("testfile") |aFile| do
    >> print a while a=aFile.gets
    >> end
    >>
    >> one will get an error indicating a doesn't exist. This error can be
    >> fixed by adding a line a="" before the print command.
    >>
    >> But logically speaking, "print a" should be interpreted after
    >> "a=File.gets". Is this because the interpreter couldn't find the object
    >> "a" when first scanning the second line?

    >
    > I suspect it's the same issue as with local variables: Ruby applies a certain
    > heuristic to determine whether something is a local var or not. This
    > heuristic is based on *syntactical* order of occurrence
    >
    >>> def foo
    >>> print a
    >>> a = 10
    >>> end

    > => nil
    >>> foo

    > NameError: undefined local variable or method `a' for main:Object
    > from (irb):2:in `foo'
    > from (irb):5


    It's also fun to see what happens if you run this kind of thing twice:

    irb(main):005:0> puts x if x = 1
    NameError: undefined local variable or method `x' for main:Object
    from (irb):5
    irb(main):006:0> puts x if x = 1
    1

    (For clarity I've deleted the warning about using '=' in conditional.
    [Matz, can't we get rid of that warning?])


    David

    --
    David A. Black
    David A. Black, Feb 13, 2005
    #4
  5. David A. Black <> wrote:

    > (For clarity I've deleted the warning about using '=' in conditional.
    > [Matz, can't we get rid of that warning?])


    I'd love per-warning suppressibility, but if not, I think this particular
    one does more good than harm. (But then, I find the if (a = f(x)) idiom
    rather ugly to begin with).

    martin
    Martin DeMello, Feb 13, 2005
    #5
  6. Hi --

    On Sun, 13 Feb 2005, Martin DeMello wrote:

    > David A. Black <> wrote:
    >
    >> (For clarity I've deleted the warning about using '=' in conditional.
    >> [Matz, can't we get rid of that warning?])

    >
    > I'd love per-warning suppressibility, but if not, I think this particular
    > one does more good than harm. (But then, I find the if (a = f(x)) idiom
    > rather ugly to begin with).


    I'm trying to figure out the pattern behind when it gets triggered or
    not:

    irb(main):002:0> while (x = 1); end
    (irb):2: warning: found = in conditional, should be ==
    irb(main):003:0> while (line = gets); end
    abc
    ^D
    => nil
    irb(main):004:0> if (m = /a/.match("b")); end
    => nil
    irb(main):005:0> if (m = /a/); end
    (irb):5: warning: found = in conditional, should be ==
    irb(main):006:0> if (m = "abc".replace("abc")); end
    => nil
    irb(main):007:0> if (m = "abc"); end
    (irb):7: warning: found = in conditional, should be ==
    => nil

    When the rhs is a literal, I guess? That at least vastly increases
    the chances of its being a case of a typo. Could it be that Matz is
    several steps ahead of me? :)


    David

    --
    David A. Black
    David A. Black, Feb 13, 2005
    #6
  7. "David A. Black" <> schrieb im Newsbeitrag
    news:pine.LNX.4.61.0502130707250.22113@wobblini...
    > Hi --
    >
    > On Sun, 13 Feb 2005, Martin DeMello wrote:
    >
    >> David A. Black <> wrote:
    >>
    >>> (For clarity I've deleted the warning about using '=' in conditional.
    >>> [Matz, can't we get rid of that warning?])

    >>
    >> I'd love per-warning suppressibility, but if not, I think this particular
    >> one does more good than harm. (But then, I find the if (a = f(x)) idiom
    >> rather ugly to begin with).

    >
    > I'm trying to figure out the pattern behind when it gets triggered or
    > not:
    >
    > irb(main):002:0> while (x = 1); end
    > (irb):2: warning: found = in conditional, should be ==
    > irb(main):003:0> while (line = gets); end
    > abc
    > ^D
    > => nil
    > irb(main):004:0> if (m = /a/.match("b")); end
    > => nil
    > irb(main):005:0> if (m = /a/); end
    > (irb):5: warning: found = in conditional, should be ==
    > irb(main):006:0> if (m = "abc".replace("abc")); end
    > => nil
    > irb(main):007:0> if (m = "abc"); end
    > (irb):7: warning: found = in conditional, should be ==
    > => nil
    >
    > When the rhs is a literal, I guess? That at least vastly increases
    > the chances of its being a case of a typo. Could it be that Matz is
    > several steps ahead of me? :)


    :))

    Note also, that assignment in a conditional really only makes sense for
    loops. With "if" and "unless" it's totally superfluous since you can always
    do

    a=x
    if a then...

    instead of

    if a=x then...

    And it's also more readable. So I would not mind if there was *always* a
    warning for assignment if it's "if" or "unless". Just my 0.02 EUR though...

    Whereas there is no easy equivalent replacement for

    while ( line = gets ) ...

    Typically, you would need two assignments which is somewhat ugly:

    line = gets
    while line
    ....
    line = gets
    end

    Kind regards

    robert
    Robert Klemme, Feb 13, 2005
    #7
  8. Hi,

    Am Montag, 14. Feb 2005, 01:39:57 +0900 schrieb Robert Klemme:
    > while ( line = gets ) ...
    >
    > Typically, you would need two assignments which is somewhat ugly:
    >
    > line = gets
    > while line
    > ....
    > line = gets
    > end


    There is

    while gets
    line = $_.chomp
    ...
    end

    Bertram

    --
    Bertram Scharpf
    Stuttgart, Deutschland/Germany
    http://www.bertram-scharpf.de
    Bertram Scharpf, Feb 13, 2005
    #8
  9. Zehao

    Jim Weirich Guest

    On Sunday 13 February 2005 11:39 am, Robert Klemme wrote:
    > Note also, that assignment in a conditional really only makes sense for
    > loops. With "if" and "unless" it's totally superfluous since you can
    > always do
    >
    > a=x
    > if a then...


    I will occasionally use the a=x in an elsif statement. Generally when the 'x'
    part looks up something that I want to process in the elsif part. E.g.

    if parent.nil?
    handle_no_parent
    elsif children = parent.get_children
    do_somthing_with(children)
    else
    do_something_else
    end

    Probably a bad example, but you get my drift.

    --
    -- Jim Weirich http://onestepback.org
    -----------------------------------------------------------------
    "Beware of bugs in the above code; I have only proved it correct,
    not tried it." -- Donald Knuth (in a memo to Peter van Emde Boas)
    Jim Weirich, Feb 13, 2005
    #9
    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. Nan Li

    evaluation order

    Nan Li, Nov 14, 2005, in forum: Java
    Replies:
    11
    Views:
    642
    Oliver Wong
    Nov 15, 2005
  2. Xavier Decoret

    Evaluation order for a=b

    Xavier Decoret, Jul 3, 2003, in forum: C++
    Replies:
    1
    Views:
    335
    Ron Natalie
    Jul 3, 2003
  3. Ilias Lazaridis
    Replies:
    2
    Views:
    381
    Ilias Lazaridis
    Apr 24, 2005
  4. Ilias Lazaridis
    Replies:
    74
    Views:
    724
    Ilias Lazaridis
    Apr 4, 2005
  5. Ilias Lazaridis
    Replies:
    18
    Views:
    322
    Bill Guindon
    Apr 9, 2005
Loading...

Share This Page