From: Damien Mattei <damien.mattei@gmail.com>
To: Per Bothner <per@bothner.com>
Cc: kawa mailing list <kawa@sourceware.org>
Subject: Re: how to know if a variable is defined
Date: Sun, 14 Apr 2024 00:58:34 +0200 [thread overview]
Message-ID: <CADEOaddBaxu4CANm0N8+rs8hxBW9vmaPKDKwyvjrKCwzpmpBHw@mail.gmail.com> (raw)
In-Reply-To: <CADEOadf2TtOWeKU_iPjiQOhYYcXLTEDcrhC0K_67VC3Ajn-cpA@mail.gmail.com>
[-- Attachment #1: Type: text/plain, Size: 6840 bytes --]
just a few add, it has nothing to see with module,the same behavior happens
at REPL and toplevel:
#|kawa:1|# (define-syntax defined-symbol?
#|.....2|# (syntax-rules ()
#|.....3|# ((_ x) (call-with-current-continuation
#|.....4|# (lambda (exit)
#|.....5|# (with-exception-handler
#|.....6|# (lambda (e)
#|.....7|# (display "defined-symbol? : undefined") (newline)
#|.....8|# (exit #f)) ; eval failed => not defined
#|.....9|# (lambda ()
#|....10|# (eval x (interaction-environment))
#|....11|# #t))))))) ; eval suceeded => defined
#|kawa:12|# (define-syntax if-defined
#|.....13|# (lambda (stx)
#|.....14|# (syntax-case stx ()
#|.....15|# ((_ id iftrue iffalse)
#|.....16|# (let ((where (defined-symbol? #'id))) ;;(quote id))))
#|.....17|# (display "if-defined : where=") (display where) (newline)
#|.....18|# (display "id=") (display #'id) (newline)
#|.....19|# (if where #'iftrue #'iffalse))))))
#|kawa:20|# (define-syntax <-
#|.....21|# (lambda (stx)
#|.....22|#
#|.....23|# (syntax-case stx ()
#|.....24|#
#|.....25|# ((_ var expr)
#|.....26|#
#|.....27|# #`(if-defined var
#|.....28|# (set! var expr)
#|.....29|# (define var expr))))))
#|kawa:30|# (define (foo)
#|.....31|# (define expr2 '())
#|.....32|#
#|.....33|# (<- expr2 7))
defined-symbol? : undefined
if-defined : where=#f
id=expr2
/dev/tty:33:7: duplicate declaration of 'expr2'
/dev/tty:31:11: (this is the previous declaration of 'expr2')
On Sun, Apr 14, 2024 at 12:45 AM Damien Mattei <damien.mattei@gmail.com>
wrote:
> hello,
>
> i ported my code from guile that use ,as you say it 'exceptions':
>
> ;; #|kawa:57|#
> ;; #|kawa:58|# (define r 2)
> ;; #|kawa:59|# (if-defined r 'defined (define r 7))
> ;;if-defined : where=#t
> ;; id=r
> ;; (if-defined r 'defined (define r 7))
> ;; defined
> ;; #|kawa:60|# r
> ;; 2
> ;; #|kawa:61|# (defined-symbol? r)
> ;; #t
> ;; #|kawa:62|# (defined-symbol? t)
> ;; /dev/tty:62:18: warning - no declaration seen for t
> ;; defined-symbol? : undefined
> ;; #f
> ;; #|kawa:63|# (let ((k 7)) (defined-symbol? k))
> ;; #t
> ;;
>
> (define-syntax defined-symbol?
> (syntax-rules ()
> ((_ x) (call-with-current-continuation
> (lambda (exit)
> (with-exception-handler
> (lambda (e)
> (display "defined-symbol? : undefined") (newline)
> (exit #f)) ; eval failed => not defined
> (lambda ()
> (eval x (interaction-environment))
> #t))))))) ; eval suceeded => defined
>
>
> ;; #|kawa:86|# (define k 0)
> ;; #|kawa:87|# (let loop () (if (< k 4) (let () (display k) (newline) (<-
> k (+ k 1)) (loop))))
> ;; if-defined : where=#t
> ;; id=k
> ;; 0
> ;; 1
> ;; 2
> ;; 3
> ;; #|kawa:88|# (let () (define k 0) (let loop () (if (< k 4) (let ()
> (display k) (newline) (<- k (+ k 1)) (loop)))))
> ;; if-defined : where=#t
> ;; id=k
> ;; 0
> ;; 1
> ;; 2
> ;; 3
> ;; #|kawa:89|# (let () (define s 0) (let loop () (if (< s 4) (let ()
> (display s) (newline) (<- s (+ s 1)) (loop)))))
> ;; if-defined : where=#t
> ;; id=s
> ;; 0
> ;; 1
> ;; 2
> ;; 3
> ;; #|kawa:90|# (let ((s 0)) (let loop () (if (< s 4) (let () (display s)
> (newline) (<- s (+ s 1)) (loop)))))
> ;; if-defined : where=#t
> ;; id=s
> ;; 0
> ;; 1
> ;; 2
> ;; 3
>
> (define-syntax if-defined
> (lambda (stx)
> (syntax-case stx ()
> ((_ id iftrue iffalse)
> (let ((where (defined-symbol? #'id))) ;;(quote id))))
> (display "if-defined : where=") (display where) (newline)
> (display "id=") (display #'id) (newline)
> (if where #'iftrue #'iffalse))))))
>
> i use the code in conjunction with this macro:
> (define-syntax <-
> (lambda (stx)
>
> (syntax-case stx ()
>
> #`(if-defined var
> (set! var expr)
> (define var expr))))))
>
> it works better than guile (guile fails on the let () tests...:
> scheme@(guile-user)> (let ((k 0)) (let loop () (if (< k 4) (let ()
> (display k) (newline) (<- k (+ k 1)) (loop)))))
> defined-symbol? : undefined
> if-defined : where=#f
> id=#<syntax:unknown file:19:72 k>
> #<unspecified>
> ice-9/boot-9.scm:1685:16: In procedure raise-exception:
> In procedure +: Wrong type argument in position 1: #<unspecified>
>
> Entering a new prompt. Type `,bt' for a backtrace or `,q' to continue.
>
> ), as you can see the examples , but in some place of my code kawa fails
> too, i made a simplified example from the whole code:
>
> for example if i put all the stuff in a module test-defined.scm:
>
> (module-name test-defined)
>
> (export foo)
>
>
>
> (define-syntax defined-symbol?
> (syntax-rules ()
> ((_ x) (call-with-current-continuation
> (lambda (exit)
> (with-exception-handler
> (lambda (e)
> (display "defined-symbol? : undefined") (newline)
> (exit #f)) ; eval failed => not defined
> (lambda ()
> (eval x (interaction-environment))
> #t))))))) ; eval suceeded => defined
>
> (define-syntax if-defined
> (lambda (stx)
> (syntax-case stx ()
> ((_ id iftrue iffalse)
> (let ((where (defined-symbol? #'id))) ;;(quote id))))
> (display "if-defined : where=") (display where) (newline)
> (display "id=") (display #'id) (newline)
> (if where #'iftrue #'iffalse))))))
>
>
>
> (define-syntax <-
> (lambda (stx)
>
> (syntax-case stx ()
>
> ((_ var expr)
>
> #`(if-defined var
> (set! var expr)
> (define var expr))))))
>
>
>
>
> (define (foo)
> (define expr2 '())
>
> (<- expr2 7))
>
> then it fails:
>
> #|kawa:1|# (require test-defined)defined-symbol? : undefined
> if-defined : where=#f
> id=expr2
> (require test-defined)
> /Users/mattei/Scheme-PLUS-for-Kawa/test-defined.scm:95:7: duplicate
> declaration of 'expr2'
> /Users/mattei/Scheme-PLUS-for-Kawa/test-defined.scm:93:11: (this is the
> previous declaration of 'expr2')
>
> it finds that expr2 is not defined,then expand a (define expr2 ...) but
> then cause an error of duplicate declaration of expr2
>
>
> On Thu, Apr 11, 2024 at 3:01 AM Per Bothner <per@bothner.com> wrote:
>
>>
>>
>> On 4/10/24 14:49, Damien Mattei via Kawa wrote:
>> > hello,
>> >
>> > is there a way to know if a variable is defined in Kawa?
>> >
>> > (like 'identifier-binding' in Racket)
>>
>> If you need to know if a variable is bound in the dynamic environment,
>> you could perhaps use eval wrapped in an exception handler.
>>
>> There are probably better ways, but I don't remember off-hand.
>>
>> Can't think of anything to use if you need information about lexical
>> bindings.
>> I supposed you could implemented identifier-binding or something similar.
>>
>> --
>> --Per Bothner
>> per@bothner.com http://per.bothner.com/
>>
>
next prev parent reply other threads:[~2024-04-13 22:58 UTC|newest]
Thread overview: 6+ messages / expand[flat|nested] mbox.gz Atom feed top
2024-04-10 21:49 Damien Mattei
2024-04-11 1:00 ` Per Bothner
2024-04-11 9:51 ` Lassi Kortela
2024-04-13 22:45 ` Damien Mattei
2024-04-13 22:58 ` Damien Mattei [this message]
2024-04-16 6:37 ` Damien Mattei
Reply instructions:
You may reply publicly to this message via plain-text email
using any one of the following methods:
* Save the following mbox file, import it into your mail client,
and reply-to-all from there: mbox
Avoid top-posting and favor interleaved quoting:
https://en.wikipedia.org/wiki/Posting_style#Interleaved_style
* Reply using the --to, --cc, and --in-reply-to
switches of git-send-email(1):
git send-email \
--in-reply-to=CADEOaddBaxu4CANm0N8+rs8hxBW9vmaPKDKwyvjrKCwzpmpBHw@mail.gmail.com \
--to=damien.mattei@gmail.com \
--cc=kawa@sourceware.org \
--cc=per@bothner.com \
/path/to/YOUR_REPLY
https://kernel.org/pub/software/scm/git/docs/git-send-email.html
* If your mail client supports setting the In-Reply-To header
via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line
before the message body.
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for read-only IMAP folder(s) and NNTP newsgroup(s).