From mboxrd@z Thu Jan 1 00:00:00 1970 Path: news.gmane.io!.POSTED.blaine.gmane.org!not-for-mail From: Zelphir Kaltstahl Newsgroups: gmane.lisp.guile.user Subject: Re: Surprising behavior of eq? Date: Sun, 20 Sep 2020 17:42:26 +0200 Message-ID: <0fd978e7-1538-fc52-a52f-d66cf57610d8@posteo.de> References: <8e1d9874-4659-cca5-03da-c2c0df102c56@posteo.de> <687423933.20200920155743@xss.de> Mime-Version: 1.0 Content-Type: text/plain; charset=utf-8 Content-Transfer-Encoding: 8bit Injection-Info: ciao.gmane.io; posting-host="blaine.gmane.org:116.202.254.214"; logging-data="14693"; mail-complaints-to="usenet@ciao.gmane.io" User-Agent: Mozilla/5.0 (X11; Linux x86_64; rv:68.0) Gecko/20100101 Thunderbird/68.10.0 Cc: guile-user@gnu.org To: Stefan Schmiedl Original-X-From: guile-user-bounces+guile-user=m.gmane-mx.org@gnu.org Sun Sep 20 17:42:46 2020 Return-path: Envelope-to: guile-user@m.gmane-mx.org Original-Received: from lists.gnu.org ([209.51.188.17]) by ciao.gmane.io with esmtps (TLS1.2:ECDHE_RSA_AES_256_GCM_SHA384:256) (Exim 4.92) (envelope-from ) id 1kK1UC-0003eV-R2 for guile-user@m.gmane-mx.org; Sun, 20 Sep 2020 17:42:44 +0200 Original-Received: from localhost ([::1]:39034 helo=lists1p.gnu.org) by lists.gnu.org with esmtp (Exim 4.90_1) (envelope-from ) id 1kK1UB-0006Ql-Ji for guile-user@m.gmane-mx.org; Sun, 20 Sep 2020 11:42:43 -0400 Original-Received: from eggs.gnu.org ([2001:470:142:3::10]:56424) by lists.gnu.org with esmtps (TLS1.2:ECDHE_RSA_AES_256_GCM_SHA384:256) (Exim 4.90_1) (envelope-from ) id 1kK1U1-0006Qd-10 for guile-user@gnu.org; Sun, 20 Sep 2020 11:42:33 -0400 Original-Received: from mout02.posteo.de ([185.67.36.66]:50451) by eggs.gnu.org with esmtps (TLS1.2:ECDHE_RSA_AES_256_GCM_SHA384:256) (Exim 4.90_1) (envelope-from ) id 1kK1Ty-0003LX-Jh for guile-user@gnu.org; Sun, 20 Sep 2020 11:42:32 -0400 Original-Received: from submission (posteo.de [89.146.220.130]) by mout02.posteo.de (Postfix) with ESMTPS id 3A7A52400FB for ; Sun, 20 Sep 2020 17:42:27 +0200 (CEST) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/simple; d=posteo.de; s=2017; t=1600616547; bh=QESeq45x8efS4v4ddbUzGqNNNWpEoxYFohMFJzz3hOo=; h=Subject:To:Cc:From:Date:From; b=T/aoQQk0tLZsPxVCVFx+iTdMteIwqzFjKKhk9bnIEG714f/SmL23kyROYF3SdP3N6 VPW4tgDR2J2aKz6WKvPqahuLgXQeeSWbLepQ92srLiaZB6qx+arZqerF+IXQx0ZnJY S4rRDvQmwzModwngRPjeHdvG1al7U5l774ocXDgbzXz0E3gdn7jhgeTXk2KfVvcj8a UjR6L/DTdabwO5XRoqLQGf3pkrprWnWh6f7AI3cGS45+ICY2aGupo88+go09kYNvU4 JiQYtGzbLXMvh8C02Eym6uVj72qDfO7ITWzluf4fDP7T0grSkEXO6tFAuB7pdLH4m4 mVtT7ntedwR9Q== Original-Received: from customer (localhost [127.0.0.1]) by submission (posteo.de) with ESMTPSA id 4BvWzQ42Xyz9rxD; Sun, 20 Sep 2020 17:42:26 +0200 (CEST) X-Tagtoolbar-Keys: D20200920174226102 In-Reply-To: <687423933.20200920155743@xss.de> Content-Language: en-US Received-SPF: pass client-ip=185.67.36.66; envelope-from=zelphirkaltstahl@posteo.de; helo=mout02.posteo.de X-detected-operating-system: by eggs.gnu.org: First seen = 2020/09/20 11:42:27 X-ACL-Warn: Detected OS = Linux 3.11 and newer [fuzzy] X-Spam_score_int: -20 X-Spam_score: -2.1 X-Spam_bar: -- X-Spam_report: (-2.1 / 5.0 requ) BAYES_00=-1.9, DKIM_SIGNED=0.1, DKIM_VALID=-0.1, DKIM_VALID_AU=-0.1, DKIM_VALID_EF=-0.1, NICE_REPLY_A=-0.001, RCVD_IN_DNSWL_NONE=-0.0001, RCVD_IN_MSPIKE_H3=-0.01, RCVD_IN_MSPIKE_WL=-0.01, SPF_HELO_NONE=0.001, SPF_PASS=-0.001 autolearn=ham autolearn_force=no X-Spam_action: no action X-BeenThere: guile-user@gnu.org X-Mailman-Version: 2.1.23 Precedence: list List-Id: General Guile related discussions List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Errors-To: guile-user-bounces+guile-user=m.gmane-mx.org@gnu.org Original-Sender: "guile-user" Xref: news.gmane.io gmane.lisp.guile.user:16937 Archived-At: Hello Stefan! Thank you for your explanation as well! On 9/20/20 3:57 PM, Stefan Schmiedl wrote: > Let's have a little shop talk with guile: > > $ guile-3.0 > GNU Guile 3.0.4-dirty > scheme@(guile-user)> (eqv? "a" "a") > $1 = #t > > Hypothesis: > guile's reader recognizes that the contents of both string literals > are the same and feeds the same string to the calling function. > > Check: > If that were the case, the two strings should not only be eqv? but > also eq? > > scheme@(guile-user)> (eq? "a" "a") > $2 = #t > > To see a different behaviour we need to avoid these literals and replace > them by values not built while reading but while executing the code: > > scheme@(guile-user)> (equal? (list->string (list #\a)) (list->string (list #\a))) > $3 = #t > > Now we compare two different string values which happen to end up with > identical content. And, behold: They are neither eqv? nor eq?. > > scheme@(guile-user)> (eqv? (list->string (list #\a)) (list->string (list #\a))) > $4 = #f > scheme@(guile-user)> (eq? (list->string (list #\a)) (list->string (list #\a))) > $5 = #f > > > Now let's see if that is consistent with the standard: > > According to r5rs, section 6.1 "Equivalence predicates": > > The eqv? procedure returns #t if: > ... > * obj1 and obj2 are pairs, vectors, or strings that denote > the same locations in the store (section 3.4). > > So we have learned > * that guile's reader reuses "store locations" for > strings of identical content I even learned a little bit about store locations and that a "store" exist as a concept in the implementation of Scheme and GNU Guile ; ) > * that eqv? is not the right predicate for content based string comparison I see! Thanks! > HTH > s. > > "Zelphir Kaltstahl" , 20.09.2020, 15:09: > >> And I've noticed something more about equality stuff in the context of >> tests: >> >> ~~~~ >> (eqv? "a" "a") >> $3 = #t >> >> ;; but >> >> (define char->>string >>   (λ (c) >>     (list->string >>      (list c)))) >> >> (import >>   ;; unit tests >>   (srfi srfi-64)) >> (test-begin "string-utils-test") >> >> (test-group >>  "char-to-string-test" >> >> (test-eqv "char->string converts a character to a string" >>  "a" >>  (char->string #\a))) >> >> (test-end "string-utils-test") >> >> %%%% Starting test string-utils-test  (Writing full log to "string-utils-test.log") >> $2 = ("string-utils-test") >> :19: FAIL char->>string converts a character to a string >> # of unexpected failures  1 >> ~~~~ >> >> So while (eqv? ...) gives the correct (?) result, the test procedure >> (test-eqv ...) which seems to indicate using (eqv? ...) via its name >> does not think of the two strings as equivalent. >> >> >> On 20.09.20 14:19, Zelphir Kaltstahl wrote: >>> Sorry, I misclicked "send" when I wanted to further edit my e-mail ... >>> >>> My Guile version is: >>> >>> ~~~~ >>> (version) >>> $6 = "3.0.4" >>> ~~~~ >>> >>> On 20.09.20 14:16, Zelphir Kaltstahl wrote: >>>> Hello Guile users, >>>> >>>> I just noticed something weird about eq?. >>>> >>>> My Guile version is: >>>> >>>> >>>> I get the different results, depending on whether I define some >>>> bindings in a let or using define: >>>> >>>> (In Emacs Geiser:) >>>> >>>> ~~~~ >>>> (define x '(10 9)) >>>> (define y '(10 9)) >>>> (eq? x y) >>>> $2 = #f >>>> >>>> (let ([x '(10 9)] >>>>       [y '(10 9)]) >>>>      (eq? x y)) >>>> $3 = #t >>>> ~~~~ >>>> >>>> Is this intentional or a bug? >>>> >>>> I first noticed something strange when writing the following code: >>>> >>>> ~~~~DEFINITION~~~~ >>>> (define make-multiple-list-remover >>>>   (λ (equal-proc) >>>>     (λ (lst unwanted) >>>>       (let loop ([remaining-list lst]) >>>>         (cond >>>>          [(null? remaining-list) >>>>           '()] >>>>          [(equal-proc (car remaining-list) unwanted) >>>>           (loop (cdr remaining-list))] >>>>          [else >>>>           (cons (car remaining-list) >>>>                 (loop (cdr remaining-list)))]))))) >>>> ~~~~ >>>> >>>> ~~~~TEST~~~~ >>>> (let ([a '(9 10)] >>>>       [b '(9 10)]) >>>>   (test-equal "make-multiple-list-remover-03" >>>>     `(1 2 (3) (4) ,a) >>>>     ((make-multiple-list-remover eq?) >>>>      `(a b (c) (d) ,a) b))) >>>> ~~~~ >>>> >>>> I was wondering, why the test fails. I think (eq? ...) should not be >>>> able to see the equivalence of both lists a and b, just like when >>>> defined using (define ...). >>>> >>>> I can also run it in the REPL and see the difference: >>>> >>>> ~~~~ >>>> (define a '(9 10)) >>>> (define b '(9 10)) >>>> ((make-multiple-list-remover eq?) >>>>  `(a b (c) (d) ,a) b) >>>> $4 = (a b (c) (d) (9 10)) >>>> >>>> (let ([a '(9 10)] >>>>       [b '(9 10)]) >>>>   ((make-multiple-list-remover eq?) >>>>    `(a b (c) (d) ,a) b)) >>>> $5 = (a b (c) (d)) >>>> ~~~~ >>>> >>>> Somehow the bindings of let seem to be different from the bindings >>>> created using define. What about using define inside let? >>>> >>>> ~~~~ >>>> >>>> ~~~~ >>>> -- >>>> repositories: https://notabug.org/ZelphirKaltstahl >>> Somehow the bindings of let seem to be different from the bindings >>> created using define. What about using define inside let? >>> >>> ~~~~ >>> (let ([unrelated 'bla]) >>>   (define a '(9 10)) >>>   (define b '(9 10)) >>>   ((make-multiple-list-remover eq?) >>>    `(a b (c) (d) ,a) b)) >>> $7 = (a b (c) (d)) >>> ~~~~ >>> >>> So there the define usage also differs from when I use define on the top >>> level. Perhaps that is the difference? On which level the bindings are >>> defined? >>> >>> Regards, >>> Zelphir >>> > > -- > Stefan Schmiedl > EDV-Beratung Schmiedl, Berghangstr. 5, 93413 Cham > Büro: +49 (0) 9971 9966 989, Mobil: +49 (0) 160 9981 6278 Best regards, Zelphir