Unlogical?


#1

Hmm, why are these two assertions breaking?

def test_strange
assert_equal true, true && true
assert_equal false, true && false
assert_equal false, false && true
assert_equal false, false && false

assert_equal true, true and true
assert_equal false, false and true
assert_equal false, false and false
assert_equal false, true and false # breaks

assert_equal true, true || true
assert_equal true, true || false
assert_equal true, false || true
assert_equal false, false || false

assert_equal true, true or true
assert_equal true, true or false
assert_equal false, false or false
assert_equal true, false or true # breaks

end

Christer


#2

-----BEGIN PGP SIGNED MESSAGE-----
Hash: SHA1

On Dec 8, 2005, at 11:40 PM, Christer N. wrote:

Hmm, why are these two assertions breaking?

assert_equal false, true or false
assert_equal(false, true) or false
assert_equal(false, (true or false))

jeremy
-----BEGIN PGP SIGNATURE-----
Version: GnuPG v1.4.2 (Darwin)

iD8DBQFDmTdlAQHALep9HFYRAj6iAJ0eukjPlXB7XIobBcqQcZbQYtE7IgCfT/Ka
0gwx518M4IXNLwdG0wTvKqM=
=1CJC
-----END PGP SIGNATURE-----


#3

On Dec 9, 2005, at 2:40 AM, Christer N. wrote:

assert_equal true, false or true # breaks

or has relatively low precedence. I imagine ruby sees assert_equal
(true, false) or true.
Try throwing in some parens eg. assert_equal(true, false or true)


#4

On Fri, 9 Dec 2005, Christer N. wrote:

Hmm, why are these two assertions breaking?

assert_equal false, true && false
assert_equal false, true and false # breaks

‘&&’ and ‘and’ have a different level of precedence, as such, the two
statements are read as:

  assert_equal (false, true && false)
  assert_equal (false, true) and false

Similar for the ‘or’. In the case of the or, you could even observe this
in irb:

irb(main):004:0> puts false || true
true
=> nil
irb(main):005:0> puts false or true
false
=> true

Since the ‘or’ has a lower precedence than the ‘||’, the ‘or’ is applied
to the result of puts, not to the parameter ‘false’.

Benedikt

ALLIANCE, n. In international politics, the union of two thieves who
have their hands so deeply inserted in each other’s pockets that
they cannot separately plunder a third.
(Ambrose Bierce, The Devil’s Dictionary)


#5

Christer N. wrote:

Maybe it has to do with parallell assignment, as the comma is used
there.

I don’t think it’s that.

My workaround will be to use “&&”

Parens will work around either.

&&, || “give” you parenthesised left and right terms -
and, or don’t.

 a && b  equates with:  (a and b)

     r = true  and  false

equates with:
((r = true) and false)

Test:
r2 = ((r = true) and false)

p [r, r2] #=> [true, false]

The following won’t make anything clearer but it
may help you to understand why it’s not clear :wink:

r = true and false ; p r #=> true
r = true and (false) ; p r #=> true
r = (true ) and false ; p r #=> true
r = true && false ; p r #=> false
r = ( true and false ) ; p r #=> false
r = ( true and (false)) ; p r #=> false
r = ((true ) and false ) ; p r #=> false
puts
r = false or true ; p r #=> false
r = false or (true ) ; p r #=> false
r = (false) or true ; p r #=> false
r = false || true ; p r #=> true
r = ( false or true ) ; p r #=> true
r = ( false or (true )) ; p r #=> true
r = ((false) or true ) ; p r #=> true

daz


#6

On Dec 9, 2005, at 3:51 AM, Christer N. wrote:

ruby wrote:

  assert_equal (false, true && false)
  assert_equal (false, true) and false

Pickaxe does not list “,” in the operator precedence table.

Because ‘,’ is not an operator. It is an argument separator.

assert_equal (false, true) and false

is the same as:

assert_equal(false,true)    and    false

I think the space between the method name and the opening
paren of the argument list is confusing you.

Gary W.


#7

ruby wrote:

  assert_equal (false, true && false)
  assert_equal (false, true) and false

Pickaxe does not list “,” in the operator precedence table.

&& || .. ... ? : = etc <<= etc defined? not or and

The only operator relating to “,” here is “=”.
Maybe it has to do with parallell assignment, as the comma is used
there.

a, b = false, true

My workaround will be to use “&&”

Christer