Are '(true nil) and '(true) is equal?

Q&A's, tips, howto's
Locked
IVShilov
Posts: 23
Joined: Wed Apr 12, 2017 1:58 am

Are '(true nil) and '(true) is equal?

Post by IVShilov »

May be I don't understand recursive comparision doing by "=", but I see no logic in this:

Code: Select all

newLISP v.10.7.1 32-bit on Windows IPv4/6 UTF-8 libffi, options: newlisp -h
> (= '(true) '(true nil))
nil
> (= '(true nil) '(true))
true
And another case on numbers:

Code: Select all

> (= '(1 0) '(1)) #-> true?
nil
>
Bug or feature?

rickyboy
Posts: 607
Joined: Fri Apr 08, 2005 7:13 pm
Location: Front Royal, Virginia

Re: Are '(true nil) and '(true) is equal?

Post by rickyboy »

Looks like a bug to me. At the very least, I believe that it should be a desirable property for the `=` operator to act as a symmetric relation, that is, that `(= a b)` and `(= b a)` return the same boolean value (for any `a` and `b`).

More fundamentally, the manual says that for all the relational operators: "List expressions can also be compared (list elements are compared recursively)." Your example of `(= '(true nil) '(true))` evaluating to `true` contradicts that assertion.

Nice find, BTW!
(λx. x x) (λx. x x)

rickyboy
Posts: 607
Joined: Fri Apr 08, 2005 7:13 pm
Location: Front Royal, Virginia

Re: Are '(true nil) and '(true) is equal?

Post by rickyboy »

Another way to exhibit the problem:

Code: Select all

> (= '(1 2 3 nil nil) '(1 2 3))
true
> (= '(1 2 3 nil nil nil) '(1 2 3))
true
> (= '(1 2 3 nil nil nil nil) '(1 2 3))
true
> ;; and so on ...
In nl-math.c, when the evaluation of any of the above expressions gets to `compareLists()` and `left` has the `nilSymbol`. `right` has the `nilCell` (because it's "bottomed out" already). Then when `compareCells(left, right)` is called, it happily reports "equal!" because `isNil(left)` (nl-math.c:1034) and `isNil(right)` (nl-math.c:1036) are both true. This is because, the `isNil()` macro doesn't distinguish between `nilSymbol` ("nil") and `nilCell` (the "end of a list" marker):

Code: Select all

newlisp.h:450:#define isNil(A) ((A)->type == CELL_NIL || ((A)->type == CELL_SYMBOL && (A)->contents == (UINT)nilSymbol))
Lutz, all the best fixing this, because I know you don't want the fix to break the behavior of the other comparison operators.
(λx. x x) (λx. x x)

Lutz
Posts: 5289
Joined: Thu Sep 26, 2002 4:45 pm
Location: Pasadena, California
Contact:

Re: Are '(true nil) and '(true) is equal?

Post by Lutz »

Thanks for the discovery of this bug.

Fixed here: http://newlisp.nfshost.com/downloads/de ... nprogress/

IVShilov
Posts: 23
Joined: Wed Apr 12, 2017 1:58 am

Re: Are '(true nil) and '(true) is equal?

Post by IVShilov »

Thank you for exhaustive answer!

IVShilov
Posts: 23
Joined: Wed Apr 12, 2017 1:58 am

Re: Are '(true nil) and '(true) is equal?

Post by IVShilov »

Lutz wrote:Thanks for the discovery of this bug.
Fixed here: http://newlisp.nfshost.com/downloads/de ... nprogress/
Thank you for nifty tool, Lutz!
NL is my pet language.

Two more questions:
1. does

Code: Select all

(letn (L '((1 2 3) (1 2 ))) (= L (transpose (transpose L)))) -> nil
have the same roots? Because L is not two-dimensional matrix, there must be an exception error, no?

2. I'm newbie in compiling on Windows, so please point me to HOWTO make newlisp.exe from sources from "http://newlisp.nfshost.com/downloads/de ... nprogress/". I need MinGW?

Lutz
Posts: 5289
Joined: Thu Sep 26, 2002 4:45 pm
Location: Pasadena, California
Contact:

Re: Are '(true nil) and '(true) is equal?

Post by Lutz »

Code: Select all

> (set 'L '((1 2 3) (1 2 )))
((1 2 3) (1 2))
> (transpose L)
((1 1) (2 2) (3 nil))
> (transpose (transpose L))
((1 2 3) (1 2 nil))
> (= L (transpose (transpose L)))
nil
> 
From the documentation of transpose :

"Any kind of list-matrix can be transposed. Matrices are made rectangular by filling in nil for missing elements, omitting elements where appropriate, or expanding atoms in rows into lists."

So this is on purpose and makes the function more usable but also will correctly make the double transposed list different from the original.

Downloads for an upcoming 10.7.5 later this spring: http://www.newlisp.org/downloads1075/

Ps: this is an 'unofficial' directory page, it might change before the actual release of v10.7.5.

IVShilov
Posts: 23
Joined: Wed Apr 12, 2017 1:58 am

Re: Are '(true nil) and '(true) is equal?

Post by IVShilov »

Ok, I understand and agree with you, add a nil to make args properly for transposition is right decision - I can filter this nil later.

But today I found that data lost because of args not matrix:

Code: Select all

> (transpose '((1) (1 2)))
((1 1))
> (transpose (transpose '((1) (1 2))))
((1) (1))
transpose throw away "2".

On a 2d-matrix, transpose is reversible:

Code: Select all

> (transpose (transpose '((1 nil) (1 2))))
((1 nil) (1 2))
May be some kind of "matrix?" predicate will be useful?
Lutz wrote: Downloads for an upcoming 10.7.5 later this spring: http://www.newlisp.org/downloads1075/
- thank you! Hope that QA-tests is up to date.

Lutz
Posts: 5289
Joined: Thu Sep 26, 2002 4:45 pm
Location: Pasadena, California
Contact:

Re: Are '(true nil) and '(true) is equal?

Post by Lutz »

From the transpose documentation:

"Matrix dimensions are calculated using the number of rows in the original matrix for columns and the number of elements in the first row as number of rows for the transposed matrix."

Looking for the shortest row in a multidimensional list would take a much longer time. So this was intentionally.

IVShilov
Posts: 23
Joined: Wed Apr 12, 2017 1:58 am

Re: Are '(true nil) and '(true) is equal?

Post by IVShilov »

Ok, thanks, question was silly.

Locked