Determining if 2 lists share a common element

45 views
Skip to first unread message

Andrew

unread,
Nov 13, 2019, 10:11:43 PM11/13/19
to Racket Users
I have this:

(define (related? a1 a2)
(if (equal? a1 a2)
true
(related? (member (rest ("proc that calls list" a1)) (rest ("proc that calls list" a2)))
(member a1 ("proc that calls list" a2))))))


a1 and a2 are part of a binary search tree and I have another function that creates a list from the elements of the tree

hence the "proc that calls list"


For some reason, whatever input I'm putting into a1 and a2 is returning only true, even when I know the answer is suppose to be false

Can anyone guide me onto what's going wrong?

George Neuner

unread,
Nov 13, 2019, 10:45:04 PM11/13/19
to Andrew, Racket Users
Just guessing, but the empty list is a member of both and all instances of '() compare eq?  (same symbol).
(eq? (list) (list))
=> #t
But if I'm understanding your code correctly, it seems like it would not work for lists of different lengths.

I think it would be simpler - and probably faster - to create an (obj -> obj)  hash[1]  using eq? compare from the elements of one list and step though the other list checking if the current element is in the hash.   Or skip the lists entirely and do it directly from the tree walks.

Hope this helps,
George

[1]  https://docs.racket-lang.org/reference/hashtables.html?q=hash#%28def._%28%28quote._~23~25kernel%29._hasheq%29%29

Luis Sanjuán

unread,
Nov 14, 2019, 3:22:55 AM11/14/19
to Racket Users
As for the lists sub-problem, a for loop can do the job:

(for*/or ([x (in-list list-1)] [y (in-list list-2)]) (equal? x y))

Alternatively, since duplicated elements don't matter, you can check the intersection:

(not (set-empty? (set-intersect list-1 list-2)))

Laurent

unread,
Nov 14, 2019, 8:17:40 AM11/14/19
to Andrew, Racket Users
On Thu, Nov 14, 2019 at 3:11 AM Andrew <ericp...@gmail.com> wrote:
I have this:

(define (related? a1 a2)
  (if (equal? a1 a2)
      true
      (related? (member (rest ("proc that calls list" a1)) (rest ("proc that calls list" a2)))
         (member a1 ("proc that calls list" a2))))))

I can't make sense of the last 2 lines. `(member x l)` returns a sublist of l starting with x if l contains x, otherwise false. If your two calls to `member` returns #f, then the next call to related? will compare (equal? #f #f) and thus return #t, which is not what you want.

Furthermore, in your first call to `member`, the first argument you pass is a list, which is suspicious.

To get a better sense of what is happening, a general advice  (works for all programming languages) is to print the values of your variables, for example:
(define (related? a1 a2)
  (displayln (list 'a1: a1 'a2: a2))
Reply all
Reply to author
Forward
0 new messages