Re: [racket-users] How to discover a struct's interface without Dr Racket?

2021-10-29 Thread 'John Clements' via Racket Users
In the text below, you refer to the “public” interface. Can I ask what you mean 
by “public” in this context?

John

> On Oct 29, 2021, at 11:16 AM, Brian Beckman  wrote:
> 
> I believe that run time will be the most plausible use case. I may write 
> macros that refer to struct-procedure names at macro-writing time, but I 
> don't expect to invoke the struct procedures at macro-expansion time. My 
> primary issue is "discoverability:" how can I find out the interface of any 
> struct?
> 
> On Thursday, October 28, 2021 at 1:00:15 PM UTC-7 jackh...@gmail.com wrote:
> Are you intending to use the struct procedure names at compile time (such as 
> in a macro) or runtime?
> 
> On Tuesday, October 26, 2021 at 5:02:46 PM UTC-7 bc.be...@gmail.com wrote:
> I understand why structs are opaque, by default, but I want to discover the 
> public interface of some struct type, that is, a list of the procedures 
> defined by the struct.
> 
> Here is an example. Suppose I want to find out all the procedures defined on 
> an instance of the syntax struct
> 
> #'42
> 
> Dr. Racket shows an expander clicky that shows some formatted information 
> inside the instance :
> 
> 
> 
> Uncapitializing the names in the display reveals the interface:
> 
> (syntax-position #'42) ~~> 790
> (syntax-span #'42) ~~> 2
> (syntax-original? #'42) ~~> #t
> 
> etc.
> 
> I want to discover those procedure names in my racket program, not manually 
> by visually inspecting graphics in Dr Racket. 
> 
> I found this trick for structs that I define:
> 
> #lang racket
> (require (for-syntax racket/struct-info))
> (require racket/pretty)
> 
> (struct foo (a b))
> (begin-for-syntax
>   (displayln 
>(extract-struct-info
> (syntax-local-value
>  #'foo
> 
> ~~>
> 
> 
> 
> but it doesn't work for the syntax type
> 
> (begin-for-syntax
>   (displayln 
>(extract-struct-info
> (syntax-local-value
>  #'syntax
> 
> ~~>
> 
> 
> 
> I'd be grateful for advice and an example of how to get the interface of 
> "syntax" without Dr Racket and without grovelling docs.
> 
> -- 
> You received this message because you are subscribed to the Google Groups 
> "Racket Users" group.
> To unsubscribe from this group and stop receiving emails from it, send an 
> email to racket-users+unsubscr...@googlegroups.com.
> To view this discussion on the web visit 
> https://groups.google.com/d/msgid/racket-users/8e4ca03e-e276-4c42-a662-4fcf7c994387n%40googlegroups.com.

-- 
You received this message because you are subscribed to the Google Groups 
"Racket Users" group.
To unsubscribe from this group and stop receiving emails from it, send an email 
to racket-users+unsubscr...@googlegroups.com.
To view this discussion on the web visit 
https://groups.google.com/d/msgid/racket-users/281a49f3-7870-48ca-888b-d3e5002b0f24%40mtasv.net.


Re: [racket-users] How to discover a struct's interface without Dr Racket?

2021-10-29 Thread Brian Beckman
Well, as I understand it, a struct (usually? always?), #:transparent or
not, when declared, defines symbols that are meant to be visible in the
current scope, so (struct foo (a b)) defines foo #|constructor|#, foo?
#|instance-predicate|# foo-a and foo-b #|data accessors|# , that I can call
on instances:

(struct foo (a b))
(let ([my-foo (foo 42 37)]
   (list (foo? my-foo)
 (foo-a my-foo)
 (foo-b my-foo)))  ~~>  '(#t 42 37)

I would like, given only the symbol foo referring to the struct type
itself, to discover (at least) the list of procedures foo?, foo-a, foo-b,
plus anything else the author of foo (the type) wants me to see.


On Fri, Oct 29, 2021 at 1:45 PM John Clements 
wrote:

> In the text below, you refer to the “public” interface. Can I ask what you
> mean by “public” in this context?
>
> John
>
> > On Oct 29, 2021, at 11:16 AM, Brian Beckman 
> wrote:
> >
> > I believe that run time will be the most plausible use case. I may write
> macros that refer to struct-procedure names at macro-writing time, but I
> don't expect to invoke the struct procedures at macro-expansion time. My
> primary issue is "discoverability:" how can I find out the interface of any
> struct?
> >
> > On Thursday, October 28, 2021 at 1:00:15 PM UTC-7 jackh...@gmail.com
> wrote:
> > Are you intending to use the struct procedure names at compile time
> (such as in a macro) or runtime?
> >
> > On Tuesday, October 26, 2021 at 5:02:46 PM UTC-7 bc.be...@gmail.com
> wrote:
> > I understand why structs are opaque, by default, but I want to discover
> the public interface of some struct type, that is, a list of the procedures
> defined by the struct.
> >
> > Here is an example. Suppose I want to find out all the procedures
> defined on an instance of the syntax struct
> >
> > #'42
> >
> > Dr. Racket shows an expander clicky that shows some formatted
> information inside the instance :
> >
> >
> >
> > Uncapitializing the names in the display reveals the interface:
> >
> > (syntax-position #'42) ~~> 790
> > (syntax-span #'42) ~~> 2
> > (syntax-original? #'42) ~~> #t
> >
> > etc.
> >
> > I want to discover those procedure names in my racket program, not
> manually by visually inspecting graphics in Dr Racket.
> >
> > I found this trick for structs that I define:
> >
> > #lang racket
> > (require (for-syntax racket/struct-info))
> > (require racket/pretty)
> >
> > (struct foo (a b))
> > (begin-for-syntax
> >   (displayln
> >(extract-struct-info
> > (syntax-local-value
> >  #'foo
> >
> > ~~>
> >
> >
> >
> > but it doesn't work for the syntax type
> >
> > (begin-for-syntax
> >   (displayln
> >(extract-struct-info
> > (syntax-local-value
> >  #'syntax
> >
> > ~~>
> >
> >
> >
> > I'd be grateful for advice and an example of how to get the interface of
> "syntax" without Dr Racket and without grovelling docs.
> >
> > --
> > You received this message because you are subscribed to the Google
> Groups "Racket Users" group.
> > To unsubscribe from this group and stop receiving emails from it, send
> an email to racket-users+unsubscr...@googlegroups.com.
> > To view this discussion on the web visit
> https://groups.google.com/d/msgid/racket-users/8e4ca03e-e276-4c42-a662-4fcf7c994387n%40googlegroups.com
> .
>
>

-- 
You received this message because you are subscribed to the Google Groups 
"Racket Users" group.
To unsubscribe from this group and stop receiving emails from it, send an email 
to racket-users+unsubscr...@googlegroups.com.
To view this discussion on the web visit 
https://groups.google.com/d/msgid/racket-users/CAK2VK6tMxFH0oEq4iCgk7PW-4yJTB8xNr_b3F6GPwQS1MZVLwQ%40mail.gmail.com.


Re: [racket-users] How to discover a struct's interface without Dr Racket?

2021-10-29 Thread Siddhartha Kasivajhula
I was able to find this interface
,
but it doesn't quite provide the same information. E.g. (struct-type-info
struct:foo)

The ability to "introspect" values in a shell (or in the application) is
useful in languages like python (e.g. dir(object) tells you what methods it
provides, help(anything) gives you the interface/function signature,
docstrings, etc.). I haven't seen this style emphasized in Racket
documentation, and that may be because racket isn't object-oriented by
default as python is, so that there often isn't a single object
encapsulating all of this information.

But all the same, if there are analogous facilities in racket, like the
kind Brian asked about, I'd love to know as well.


On Fri, Oct 29, 2021 at 3:14 PM Brian Beckman  wrote:

> Well, as I understand it, a struct (usually? always?), #:transparent or
> not, when declared, defines symbols that are meant to be visible in the
> current scope, so (struct foo (a b)) defines foo #|constructor|#, foo?
> #|instance-predicate|# foo-a and foo-b #|data accessors|# , that I can call
> on instances:
>
> (struct foo (a b))
> (let ([my-foo (foo 42 37)]
>(list (foo? my-foo)
>  (foo-a my-foo)
>  (foo-b my-foo)))  ~~>  '(#t 42 37)
>
> I would like, given only the symbol foo referring to the struct type
> itself, to discover (at least) the list of procedures foo?, foo-a, foo-b,
> plus anything else the author of foo (the type) wants me to see.
>
>
> On Fri, Oct 29, 2021 at 1:45 PM John Clements 
> wrote:
>
>> In the text below, you refer to the “public” interface. Can I ask what
>> you mean by “public” in this context?
>>
>> John
>>
>> > On Oct 29, 2021, at 11:16 AM, Brian Beckman 
>> wrote:
>> >
>> > I believe that run time will be the most plausible use case. I may
>> write macros that refer to struct-procedure names at macro-writing time,
>> but I don't expect to invoke the struct procedures at macro-expansion time.
>> My primary issue is "discoverability:" how can I find out the interface of
>> any struct?
>> >
>> > On Thursday, October 28, 2021 at 1:00:15 PM UTC-7 jackh...@gmail.com
>> wrote:
>> > Are you intending to use the struct procedure names at compile time
>> (such as in a macro) or runtime?
>> >
>> > On Tuesday, October 26, 2021 at 5:02:46 PM UTC-7 bc.be...@gmail.com
>> wrote:
>> > I understand why structs are opaque, by default, but I want to discover
>> the public interface of some struct type, that is, a list of the procedures
>> defined by the struct.
>> >
>> > Here is an example. Suppose I want to find out all the procedures
>> defined on an instance of the syntax struct
>> >
>> > #'42
>> >
>> > Dr. Racket shows an expander clicky that shows some formatted
>> information inside the instance :
>> >
>> >
>> >
>> > Uncapitializing the names in the display reveals the interface:
>> >
>> > (syntax-position #'42) ~~> 790
>> > (syntax-span #'42) ~~> 2
>> > (syntax-original? #'42) ~~> #t
>> >
>> > etc.
>> >
>> > I want to discover those procedure names in my racket program, not
>> manually by visually inspecting graphics in Dr Racket.
>> >
>> > I found this trick for structs that I define:
>> >
>> > #lang racket
>> > (require (for-syntax racket/struct-info))
>> > (require racket/pretty)
>> >
>> > (struct foo (a b))
>> > (begin-for-syntax
>> >   (displayln
>> >(extract-struct-info
>> > (syntax-local-value
>> >  #'foo
>> >
>> > ~~>
>> >
>> >
>> >
>> > but it doesn't work for the syntax type
>> >
>> > (begin-for-syntax
>> >   (displayln
>> >(extract-struct-info
>> > (syntax-local-value
>> >  #'syntax
>> >
>> > ~~>
>> >
>> >
>> >
>> > I'd be grateful for advice and an example of how to get the interface
>> of "syntax" without Dr Racket and without grovelling docs.
>> >
>> > --
>> > You received this message because you are subscribed to the Google
>> Groups "Racket Users" group.
>> > To unsubscribe from this group and stop receiving emails from it, send
>> an email to racket-users+unsubscr...@googlegroups.com.
>> > To view this discussion on the web visit
>> https://groups.google.com/d/msgid/racket-users/8e4ca03e-e276-4c42-a662-4fcf7c994387n%40googlegroups.com
>> .
>>
>> --
> You received this message because you are subscribed to the Google Groups
> "Racket Users" group.
> To unsubscribe from this group and stop receiving emails from it, send an
> email to racket-users+unsubscr...@googlegroups.com.
> To view this discussion on the web visit
> https://groups.google.com/d/msgid/racket-users/CAK2VK6tMxFH0oEq4iCgk7PW-4yJTB8xNr_b3F6GPwQS1MZVLwQ%40mail.gmail.com
> 
> .
>

-- 
You received this message because you are subscribed to the Google Groups 
"Racket Users" group.
To unsubscribe from this grou

Re: [racket-users] How to discover a struct's interface without Dr Racket?

2021-10-30 Thread Brian Beckman
Here are some of my latest (failed) experiments:

#lang racket

(require (for-syntax racket/struct-info))
(require racket/pretty)

(struct foo (a b) #:transparent)

(displayln `("a foo object is transparent: I can see inside: \n  
(struct->vector (foo 1 2)) ~~> "
 ,(struct->vector (foo 1 2

(displayln `("syntax object is opaque I can't see inside: \n  
(struct->vector #'foo) ~~> "
 ,(struct->vector #'foo)))

;;; Why do two copies of the syntax display? (One copy
;;; is a side-effect. The other is a result).

;;; At expansion time, I can get some graphics in Dr-Racket for
;;; definition of foo, but I cannot get likewise 
;;; not into the definition of syntax. 
(begin-for-syntax
  (displayln 
   (extract-struct-info
(syntax-local-value
 #'foo  ; #'syntax

;;; But the access procedures for #'syntax are known!?!? (I just
;;; happen to know that there is a procedure named 'syntax-position';
;;; my whole issue is in trying to find out the list of all
;;; procedures defined in the system when the syntax type is created!)

(syntax-position #'42)

;;; Whereas #'foo is known in this module scope,
;;; (syntax struct:foo) is not known! Looks like the shorthand
;;; #'whatever for making a syntax object is known, but the longhand,
;;; presumably (syntax 'whatever), is not known.

(begin-for-syntax
  (displayln 
   (extract-struct-info
(syntax-local-value
 #'syntax



Welcome to DrRacket, version 8.2 [cs].
Language: racket, with debugging; memory limit: 128 MB.
(.# 
.# 
.# 
(.# 
.#) (#f #f) #t)
. . 
../../../../../../usr/share/racket/pkgs/errortrace-lib/errortrace/stacktrace.rkt:690:2:
 
extract-struct-info: contract violation
  expected: struct-info?
  given: #
> 

On Friday, October 29, 2021 at 4:10:37 PM UTC-7 Siddhartha Kasivajhula 
wrote:

> I was able to find this interface 
> ,
>  
> but it doesn't quite provide the same information. E.g. (struct-type-info 
> struct:foo)
>
> The ability to "introspect" values in a shell (or in the application) is 
> useful in languages like python (e.g. dir(object) tells you what methods 
> it provides, help(anything) gives you the interface/function signature, 
> docstrings, etc.). I haven't seen this style emphasized in Racket 
> documentation, and that may be because racket isn't object-oriented by 
> default as python is, so that there often isn't a single object 
> encapsulating all of this information.
>
> But all the same, if there are analogous facilities in racket, like the 
> kind Brian asked about, I'd love to know as well.
>
>
> On Fri, Oct 29, 2021 at 3:14 PM Brian Beckman  wrote:
>
>> Well, as I understand it, a struct (usually? always?), #:transparent or 
>> not, when declared, defines symbols that are meant to be visible in the 
>> current scope, so (struct foo (a b)) defines foo #|constructor|#, foo? 
>> #|instance-predicate|# foo-a and foo-b #|data accessors|# , that I can call 
>> on instances:
>>
>> (struct foo (a b))
>> (let ([my-foo (foo 42 37)]
>>(list (foo? my-foo) 
>>  (foo-a my-foo) 
>>  (foo-b my-foo)))  ~~>  '(#t 42 37)
>>
>> I would like, given only the symbol foo referring to the struct type 
>> itself, to discover (at least) the list of procedures foo?, foo-a, foo-b, 
>> plus anything else the author of foo (the type) wants me to see.
>> 
>>
>> On Fri, Oct 29, 2021 at 1:45 PM John Clements  
>> wrote:
>>
>>> In the text below, you refer to the “public” interface. Can I ask what 
>>> you mean by “public” in this context?
>>>
>>> John
>>>
>>> > On Oct 29, 2021, at 11:16 AM, Brian Beckman  
>>> wrote:
>>> > 
>>> > I believe that run time will be the most plausible use case. I may 
>>> write macros that refer to struct-procedure names at macro-writing time, 
>>> but I don't expect to invoke the struct procedures at macro-expansion time. 
>>> My primary issue is "discoverability:" how can I find out the interface of 
>>> any struct?
>>> > 
>>> > On Thursday, October 28, 2021 at 1:00:15 PM UTC-7 jackh...@gmail.com 
>>> wrote:
>>> > Are you intending to use the struct procedure names at compile time 
>>> (such as in a macro) or runtime?
>>> > 
>>> > On Tuesday, October 26, 2021 at 5:02:46 PM UTC-7 bc.be...@gmail.com 
>>> wrote:
>>> > I understand why structs are opaque, by default, but I want to 
>>> discover the public interface of some struct type, that is, a list of the 
>>> procedures defined by the struct.
>>> > 
>>> > Here is an example. Suppose I want to find out all the procedures 
>>> defined on an instance of the syntax struct
>>> > 
>>> > #'42
>>> > 
>>> > Dr. Racket shows an expander clicky that shows some formatted 
>>> information inside the instance :
>>> > 
>>> > 
>>> > 
>>> > Uncapitializing the names in the display reveals the interface:
>>> > 
>>> > (syntax-position #'42) ~~> 790
>>> > (syntax-span #'42) ~

Re: [racket-users] How to discover a struct's interface without Dr Racket?

2021-10-31 Thread Matt Jadud
Hi Brian,

Does this help move you forward?

It has been a while since I've stared at macros in Racket, so this might be
easier...

Also, make sure you're executing this code in a module. If you're working
in a REPL, I suspect all bets are off. It is certainly the case that you
could combine several of my exploration steps into a simpler/cleaner macro,
instead of generating lists of symbols, converting them back to syntax
objects, and so on.

Also, as a solution/exploration, I... don't know how this would interact
with the full range of possible structs. Someone who knows more about
syntax and structs should be able to speak to how you'd find out all of the
defined functions that spawn from struct definition/creation. (It might
also be useful to know *why* you want to destructure structs this way?
Knowing that may illuminate some other path forward.)

#lang racket
(require racket/struct-info)

(struct A (b c))

(struct B (e f) #:transparent)

(require (for-syntax racket/struct-info))
(define-syntax (get-field-names stx)
  (syntax-case stx ()
[(_ sym)
 #`(quote
#,(struct-field-info-list
   (syntax-local-value #'sym)))
  ]))

;; These let me see the field names
(get-field-names A)
;; Returns '(c b)
(get-field-names B)
;; Returns '(f e)

;;
https://stackoverflow.com/questions/20076868/how-to-know-whether-a-racket-variable-is-defined-or-not
(define-syntax (defined? stx)
  (syntax-case stx ()
[(_ id)
 (with-syntax ([v (identifier-binding #'id)])
   #''v)]))

(define-syntax (proc-names stx)
  (syntax-case stx ()
[(_ sym)
 (let ([names (map (λ (s)
 (string->symbol
  (format "~a-~a" (syntax-e #'sym) s)))
   (struct-field-info-list
(syntax-local-value #'sym))
   )])
   #`(quote #,names))]))

;; This...
(proc-names A)
;; Returns '(A-c A-b)

(define-syntax (names-exist? stx)
  (syntax-case stx ()
[(_ sym)
 (let ([names (map (λ (s)
 (string->symbol
  (format "~a-~a" (syntax-e #'sym) s)))
   (struct-field-info-list
(syntax-local-value #'sym))
   )])
   #`(andmap (λ (s)
   (equal? 'lexical s))
 (map (λ (s)
(defined? s))
  (quote #,names)))
   )]))

(names-exist? A)
(names-exist? B)


On Sat, Oct 30, 2021 at 10:33 PM Brian Beckman  wrote:

> Here are some of my latest (failed) experiments:
>
> #lang racket
>
> (require (for-syntax racket/struct-info))
> (require racket/pretty)
>
> (struct foo (a b) #:transparent)
>
> (displayln `("a foo object is transparent: I can see inside: \n
> (struct->vector (foo 1 2)) ~~> "
>  ,(struct->vector (foo 1 2
>
> (displayln `("syntax object is opaque I can't see inside: \n
> (struct->vector #'foo) ~~> "
>  ,(struct->vector #'foo)))
>
> ;;; Why do two copies of the syntax display? (One copy
> ;;; is a side-effect. The other is a result).
>
> ;;; At expansion time, I can get some graphics in Dr-Racket for
> ;;; definition of foo, but I cannot get likewise
> ;;; not into the definition of syntax.
> (begin-for-syntax
>   (displayln
>(extract-struct-info
> (syntax-local-value
>  #'foo  ; #'syntax
>
> ;;; But the access procedures for #'syntax are known!?!? (I just
> ;;; happen to know that there is a procedure named 'syntax-position';
> ;;; my whole issue is in trying to find out the list of all
> ;;; procedures defined in the system when the syntax type is created!)
>
> (syntax-position #'42)
>
> ;;; Whereas #'foo is known in this module scope,
> ;;; (syntax struct:foo) is not known! Looks like the shorthand
> ;;; #'whatever for making a syntax object is known, but the longhand,
> ;;; presumably (syntax 'whatever), is not known.
>
> (begin-for-syntax
>   (displayln
>(extract-struct-info
> (syntax-local-value
>  #'syntax
>
> 
>
> Welcome to DrRacket, version 8.2 [cs].
> Language: racket, with debugging; memory limit: 128 MB.
> (.# struct:foo>
> .# foo>
> .# foo?>
> (.# foo-b>
> .# foo-a>) (#f #f) #t)
> . .
> ../../../../../../usr/share/racket/pkgs/errortrace-lib/errortrace/stacktrace.rkt:690:2:
> extract-struct-info: contract violation
>   expected: struct-info?
>   given: #
> >
>
> On Friday, October 29, 2021 at 4:10:37 PM UTC-7 Siddhartha Kasivajhula
> wrote:
>
>> I was able to find this interface
>> ,
>> but it doesn't quite provide the same information. E.g. (struct-type-info
>> struct:foo)
>>
>> The ability to "introspect" values in a shell (or in the application) is
>> useful in languages like python (e.g. dir(object) tells you what methods
>> it provides, help(anything) gives you the interface/function signature,
>> docstrings, etc

Re: [racket-users] How to discover a struct's interface without Dr Racket?

2021-10-31 Thread Jens Axel Søgaard
Hi Brian,

A few random thoughts:

> I would like, given only the symbol foo referring to the struct type
itself,
> to discover (at least) the list of procedures foo?, foo-a, foo-b, plus
> anything else the author of foo (the type) wants me to see.

When you want to look this up, is it in the repl (i.e. at runtime)?

The standard `struct` construct doesn't store much reflection information.
Instead of fighting the standard construct, you can consider making a
little variation.

If you are satisfied with having info for the structs defined in your own
program
(i.e. modules you have written yourself), then you can consider making a
module, say, `fancy-struct` that exports a macro where

   (fancy-struct yada ...)

expands into

   (begin
  (fancy-struct yada ...)
  )

Using `rename-out` you can export it as `struct`, so it can be used without
changing any existing code.

/Jens Axel


Den søn. 31. okt. 2021 kl. 11.42 skrev Matt Jadud :

> Hi Brian,
>
> Does this help move you forward?
>
> It has been a while since I've stared at macros in Racket, so this might
> be easier...
>
> Also, make sure you're executing this code in a module. If you're working
> in a REPL, I suspect all bets are off. It is certainly the case that you
> could combine several of my exploration steps into a simpler/cleaner macro,
> instead of generating lists of symbols, converting them back to syntax
> objects, and so on.
>
> Also, as a solution/exploration, I... don't know how this would interact
> with the full range of possible structs. Someone who knows more about
> syntax and structs should be able to speak to how you'd find out all of the
> defined functions that spawn from struct definition/creation. (It might
> also be useful to know *why* you want to destructure structs this way?
> Knowing that may illuminate some other path forward.)
>
> #lang racket
> (require racket/struct-info)
>
> (struct A (b c))
>
> (struct B (e f) #:transparent)
>
> (require (for-syntax racket/struct-info))
> (define-syntax (get-field-names stx)
>   (syntax-case stx ()
> [(_ sym)
>  #`(quote
> #,(struct-field-info-list
>(syntax-local-value #'sym)))
>   ]))
>
> ;; These let me see the field names
> (get-field-names A)
> ;; Returns '(c b)
> (get-field-names B)
> ;; Returns '(f e)
>
> ;;
> https://stackoverflow.com/questions/20076868/how-to-know-whether-a-racket-variable-is-defined-or-not
> (define-syntax (defined? stx)
>   (syntax-case stx ()
> [(_ id)
>  (with-syntax ([v (identifier-binding #'id)])
>#''v)]))
>
> (define-syntax (proc-names stx)
>   (syntax-case stx ()
> [(_ sym)
>  (let ([names (map (λ (s)
>  (string->symbol
>   (format "~a-~a" (syntax-e #'sym) s)))
>(struct-field-info-list
> (syntax-local-value #'sym))
>)])
>#`(quote #,names))]))
>
> ;; This...
> (proc-names A)
> ;; Returns '(A-c A-b)
>
> (define-syntax (names-exist? stx)
>   (syntax-case stx ()
> [(_ sym)
>  (let ([names (map (λ (s)
>  (string->symbol
>   (format "~a-~a" (syntax-e #'sym) s)))
>(struct-field-info-list
> (syntax-local-value #'sym))
>)])
>#`(andmap (λ (s)
>(equal? 'lexical s))
>  (map (λ (s)
> (defined? s))
>   (quote #,names)))
>)]))
>
> (names-exist? A)
> (names-exist? B)
>
>
> On Sat, Oct 30, 2021 at 10:33 PM Brian Beckman 
> wrote:
>
>> Here are some of my latest (failed) experiments:
>>
>> #lang racket
>>
>> (require (for-syntax racket/struct-info))
>> (require racket/pretty)
>>
>> (struct foo (a b) #:transparent)
>>
>> (displayln `("a foo object is transparent: I can see inside: \n
>> (struct->vector (foo 1 2)) ~~> "
>>  ,(struct->vector (foo 1 2
>>
>> (displayln `("syntax object is opaque I can't see inside: \n
>> (struct->vector #'foo) ~~> "
>>  ,(struct->vector #'foo)))
>>
>> ;;; Why do two copies of the syntax display? (One copy
>> ;;; is a side-effect. The other is a result).
>>
>> ;;; At expansion time, I can get some graphics in Dr-Racket for
>> ;;; definition of foo, but I cannot get likewise
>> ;;; not into the definition of syntax.
>> (begin-for-syntax
>>   (displayln
>>(extract-struct-info
>> (syntax-local-value
>>  #'foo  ; #'syntax
>>
>> ;;; But the access procedures for #'syntax are known!?!? (I just
>> ;;; happen to know that there is a procedure named 'syntax-position';
>> ;;; my whole issue is in trying to find out the list of all
>> ;;; procedures defined in the system when the syntax type is created!)
>>
>> (syntax-position #'42)
>>
>> ;;; Whereas #'foo is known in this module scope,
>> ;;; (syntax struct:foo) is not known! Looks like the shorthand
>> ;;; #'whatever for making a syntax

Re: [racket-users] How to discover a struct's interface without Dr Racket?

2021-10-31 Thread David Storrs
On Sun, Oct 31, 2021, 7:49 AM Jens Axel Søgaard 
wrote:

> Hi Brian,
>
> A few random thoughts:
>
> > I would like, given only the symbol foo referring to the struct type
> itself,
> > to discover (at least) the list of procedures foo?, foo-a, foo-b, plus
> > anything else the author of foo (the type) wants me to see.
>
> When you want to look this up, is it in the repl (i.e. at runtime)?
>
> The standard `struct` construct doesn't store much reflection information.
> Instead of fighting the standard construct, you can consider making a
> little variation.
>
> If you are satisfied with having info for the structs defined in your own
> program
> (i.e. modules you have written yourself), then you can consider making a
> module, say, `fancy-struct` that exports a macro where
>
>(fancy-struct yada ...)
>
> expands into
>
>(begin
>   (fancy-struct yada ...)
>   )
>
> Using `rename-out` you can export it as `struct`, so it can be used
> without changing any existing code.
>
> /Jens Axel
>

Coincidentally, that module exists!

https://docs.racket-lang.org/struct-plus-plus/index.html#%28part._.Reflection%29



>
>
> Den søn. 31. okt. 2021 kl. 11.42 skrev Matt Jadud :
>
>> Hi Brian,
>>
>> Does this help move you forward?
>>
>> It has been a while since I've stared at macros in Racket, so this might
>> be easier...
>>
>> Also, make sure you're executing this code in a module. If you're working
>> in a REPL, I suspect all bets are off. It is certainly the case that you
>> could combine several of my exploration steps into a simpler/cleaner macro,
>> instead of generating lists of symbols, converting them back to syntax
>> objects, and so on.
>>
>> Also, as a solution/exploration, I... don't know how this would interact
>> with the full range of possible structs. Someone who knows more about
>> syntax and structs should be able to speak to how you'd find out all of the
>> defined functions that spawn from struct definition/creation. (It might
>> also be useful to know *why* you want to destructure structs this way?
>> Knowing that may illuminate some other path forward.)
>>
>> #lang racket
>> (require racket/struct-info)
>>
>> (struct A (b c))
>>
>> (struct B (e f) #:transparent)
>>
>> (require (for-syntax racket/struct-info))
>> (define-syntax (get-field-names stx)
>>   (syntax-case stx ()
>> [(_ sym)
>>  #`(quote
>> #,(struct-field-info-list
>>(syntax-local-value #'sym)))
>>   ]))
>>
>> ;; These let me see the field names
>> (get-field-names A)
>> ;; Returns '(c b)
>> (get-field-names B)
>> ;; Returns '(f e)
>>
>> ;;
>> https://stackoverflow.com/questions/20076868/how-to-know-whether-a-racket-variable-is-defined-or-not
>> (define-syntax (defined? stx)
>>   (syntax-case stx ()
>> [(_ id)
>>  (with-syntax ([v (identifier-binding #'id)])
>>#''v)]))
>>
>> (define-syntax (proc-names stx)
>>   (syntax-case stx ()
>> [(_ sym)
>>  (let ([names (map (λ (s)
>>  (string->symbol
>>   (format "~a-~a" (syntax-e #'sym) s)))
>>(struct-field-info-list
>> (syntax-local-value #'sym))
>>)])
>>#`(quote #,names))]))
>>
>> ;; This...
>> (proc-names A)
>> ;; Returns '(A-c A-b)
>>
>> (define-syntax (names-exist? stx)
>>   (syntax-case stx ()
>> [(_ sym)
>>  (let ([names (map (λ (s)
>>  (string->symbol
>>   (format "~a-~a" (syntax-e #'sym) s)))
>>(struct-field-info-list
>> (syntax-local-value #'sym))
>>)])
>>#`(andmap (λ (s)
>>(equal? 'lexical s))
>>  (map (λ (s)
>> (defined? s))
>>   (quote #,names)))
>>)]))
>>
>> (names-exist? A)
>> (names-exist? B)
>>
>>
>> On Sat, Oct 30, 2021 at 10:33 PM Brian Beckman 
>> wrote:
>>
>>> Here are some of my latest (failed) experiments:
>>>
>>> #lang racket
>>>
>>> (require (for-syntax racket/struct-info))
>>> (require racket/pretty)
>>>
>>> (struct foo (a b) #:transparent)
>>>
>>> (displayln `("a foo object is transparent: I can see inside: \n
>>> (struct->vector (foo 1 2)) ~~> "
>>>  ,(struct->vector (foo 1 2
>>>
>>> (displayln `("syntax object is opaque I can't see inside: \n
>>> (struct->vector #'foo) ~~> "
>>>  ,(struct->vector #'foo)))
>>>
>>> ;;; Why do two copies of the syntax display? (One copy
>>> ;;; is a side-effect. The other is a result).
>>>
>>> ;;; At expansion time, I can get some graphics in Dr-Racket for
>>> ;;; definition of foo, but I cannot get likewise
>>> ;;; not into the definition of syntax.
>>> (begin-for-syntax
>>>   (displayln
>>>(extract-struct-info
>>> (syntax-local-value
>>>  #'foo  ; #'syntax
>>>
>>> ;;; But the access procedures for #'syntax are known!?!? (I just
>>> ;;; happen to know that there is a 

Re: [racket-users] How to discover a struct's interface without Dr Racket?

2021-10-31 Thread Jens Axel Søgaard
A quick example:

#lang racket
(require racket/require)
(require (filtered-in (λ (name) (regexp-replace #rx"struct[+][+]" name
"struct"))
  struct-plus-plus))

(struct horse (breed color legs))

(define beauty (horse 'arabian 'black 4))

(define info (force (struct-ref beauty)))
(map struct-field-name (struct-info-fields info))

The result is:
'(breed color legs)

Den søn. 31. okt. 2021 kl. 13.06 skrev David Storrs :

>
>
> On Sun, Oct 31, 2021, 7:49 AM Jens Axel Søgaard 
> wrote:
>
>> Hi Brian,
>>
>> A few random thoughts:
>>
>> > I would like, given only the symbol foo referring to the struct type
>> itself,
>> > to discover (at least) the list of procedures foo?, foo-a, foo-b, plus
>> > anything else the author of foo (the type) wants me to see.
>>
>> When you want to look this up, is it in the repl (i.e. at runtime)?
>>
>> The standard `struct` construct doesn't store much reflection information.
>> Instead of fighting the standard construct, you can consider making a
>> little variation.
>>
>> If you are satisfied with having info for the structs defined in your own
>> program
>> (i.e. modules you have written yourself), then you can consider making a
>> module, say, `fancy-struct` that exports a macro where
>>
>>(fancy-struct yada ...)
>>
>> expands into
>>
>>(begin
>>   (fancy-struct yada ...)
>>   )
>>
>> Using `rename-out` you can export it as `struct`, so it can be used
>> without changing any existing code.
>>
>> /Jens Axel
>>
>
> Coincidentally, that module exists!
>
>
> https://docs.racket-lang.org/struct-plus-plus/index.html#%28part._.Reflection%29
>
>
>
>>
>>
>> Den søn. 31. okt. 2021 kl. 11.42 skrev Matt Jadud :
>>
>>> Hi Brian,
>>>
>>> Does this help move you forward?
>>>
>>> It has been a while since I've stared at macros in Racket, so this might
>>> be easier...
>>>
>>> Also, make sure you're executing this code in a module. If you're
>>> working in a REPL, I suspect all bets are off. It is certainly the case
>>> that you could combine several of my exploration steps into a
>>> simpler/cleaner macro, instead of generating lists of symbols, converting
>>> them back to syntax objects, and so on.
>>>
>>> Also, as a solution/exploration, I... don't know how this would interact
>>> with the full range of possible structs. Someone who knows more about
>>> syntax and structs should be able to speak to how you'd find out all of the
>>> defined functions that spawn from struct definition/creation. (It might
>>> also be useful to know *why* you want to destructure structs this way?
>>> Knowing that may illuminate some other path forward.)
>>>
>>> #lang racket
>>> (require racket/struct-info)
>>>
>>> (struct A (b c))
>>>
>>> (struct B (e f) #:transparent)
>>>
>>> (require (for-syntax racket/struct-info))
>>> (define-syntax (get-field-names stx)
>>>   (syntax-case stx ()
>>> [(_ sym)
>>>  #`(quote
>>> #,(struct-field-info-list
>>>(syntax-local-value #'sym)))
>>>   ]))
>>>
>>> ;; These let me see the field names
>>> (get-field-names A)
>>> ;; Returns '(c b)
>>> (get-field-names B)
>>> ;; Returns '(f e)
>>>
>>> ;;
>>> https://stackoverflow.com/questions/20076868/how-to-know-whether-a-racket-variable-is-defined-or-not
>>> (define-syntax (defined? stx)
>>>   (syntax-case stx ()
>>> [(_ id)
>>>  (with-syntax ([v (identifier-binding #'id)])
>>>#''v)]))
>>>
>>> (define-syntax (proc-names stx)
>>>   (syntax-case stx ()
>>> [(_ sym)
>>>  (let ([names (map (λ (s)
>>>  (string->symbol
>>>   (format "~a-~a" (syntax-e #'sym) s)))
>>>(struct-field-info-list
>>> (syntax-local-value #'sym))
>>>)])
>>>#`(quote #,names))]))
>>>
>>> ;; This...
>>> (proc-names A)
>>> ;; Returns '(A-c A-b)
>>>
>>> (define-syntax (names-exist? stx)
>>>   (syntax-case stx ()
>>> [(_ sym)
>>>  (let ([names (map (λ (s)
>>>  (string->symbol
>>>   (format "~a-~a" (syntax-e #'sym) s)))
>>>(struct-field-info-list
>>> (syntax-local-value #'sym))
>>>)])
>>>#`(andmap (λ (s)
>>>(equal? 'lexical s))
>>>  (map (λ (s)
>>> (defined? s))
>>>   (quote #,names)))
>>>)]))
>>>
>>> (names-exist? A)
>>> (names-exist? B)
>>>
>>>
>>> On Sat, Oct 30, 2021 at 10:33 PM Brian Beckman 
>>> wrote:
>>>
 Here are some of my latest (failed) experiments:

 #lang racket

 (require (for-syntax racket/struct-info))
 (require racket/pretty)

 (struct foo (a b) #:transparent)

 (displayln `("a foo object is transparent: I can see inside: \n
 (struct->vector (foo 1 2)) ~~> "
  ,(struct->vector (foo 1 2

 (displayln `("syntax object is opaque I can't see inside: \

Re: [racket-users] How to discover a struct's interface without Dr Racket?

2021-10-31 Thread David Storrs
The actual accessor functions are in there as well, not just the names.

On Sun, Oct 31, 2021, 9:58 AM Jens Axel Søgaard 
wrote:

> A quick example:
>
> #lang racket
> (require racket/require)
> (require (filtered-in (λ (name) (regexp-replace #rx"struct[+][+]" name
> "struct"))
>   struct-plus-plus))
>
> (struct horse (breed color legs))
>
> (define beauty (horse 'arabian 'black 4))
>
> (define info (force (struct-ref beauty)))
> (map struct-field-name (struct-info-fields info))
>
> The result is:
> '(breed color legs)
>
> Den søn. 31. okt. 2021 kl. 13.06 skrev David Storrs <
> david.sto...@gmail.com>:
>
>>
>>
>> On Sun, Oct 31, 2021, 7:49 AM Jens Axel Søgaard 
>> wrote:
>>
>>> Hi Brian,
>>>
>>> A few random thoughts:
>>>
>>> > I would like, given only the symbol foo referring to the struct type
>>> itself,
>>> > to discover (at least) the list of procedures foo?, foo-a, foo-b, plus
>>> > anything else the author of foo (the type) wants me to see.
>>>
>>> When you want to look this up, is it in the repl (i.e. at runtime)?
>>>
>>> The standard `struct` construct doesn't store much reflection
>>> information.
>>> Instead of fighting the standard construct, you can consider making a
>>> little variation.
>>>
>>> If you are satisfied with having info for the structs defined in your
>>> own program
>>> (i.e. modules you have written yourself), then you can consider making a
>>> module, say, `fancy-struct` that exports a macro where
>>>
>>>(fancy-struct yada ...)
>>>
>>> expands into
>>>
>>>(begin
>>>   (fancy-struct yada ...)
>>>   )
>>>
>>> Using `rename-out` you can export it as `struct`, so it can be used
>>> without changing any existing code.
>>>
>>> /Jens Axel
>>>
>>
>> Coincidentally, that module exists!
>>
>>
>> https://docs.racket-lang.org/struct-plus-plus/index.html#%28part._.Reflection%29
>>
>>
>>
>>>
>>>
>>> Den søn. 31. okt. 2021 kl. 11.42 skrev Matt Jadud :
>>>
 Hi Brian,

 Does this help move you forward?

 It has been a while since I've stared at macros in Racket, so this
 might be easier...

 Also, make sure you're executing this code in a module. If you're
 working in a REPL, I suspect all bets are off. It is certainly the case
 that you could combine several of my exploration steps into a
 simpler/cleaner macro, instead of generating lists of symbols, converting
 them back to syntax objects, and so on.

 Also, as a solution/exploration, I... don't know how this would
 interact with the full range of possible structs. Someone who knows more
 about syntax and structs should be able to speak to how you'd find out all
 of the defined functions that spawn from struct definition/creation. (It
 might also be useful to know *why* you want to destructure structs this
 way? Knowing that may illuminate some other path forward.)

 #lang racket
 (require racket/struct-info)

 (struct A (b c))

 (struct B (e f) #:transparent)

 (require (for-syntax racket/struct-info))
 (define-syntax (get-field-names stx)
   (syntax-case stx ()
 [(_ sym)
  #`(quote
 #,(struct-field-info-list
(syntax-local-value #'sym)))
   ]))

 ;; These let me see the field names
 (get-field-names A)
 ;; Returns '(c b)
 (get-field-names B)
 ;; Returns '(f e)

 ;;
 https://stackoverflow.com/questions/20076868/how-to-know-whether-a-racket-variable-is-defined-or-not
 (define-syntax (defined? stx)
   (syntax-case stx ()
 [(_ id)
  (with-syntax ([v (identifier-binding #'id)])
#''v)]))

 (define-syntax (proc-names stx)
   (syntax-case stx ()
 [(_ sym)
  (let ([names (map (λ (s)
  (string->symbol
   (format "~a-~a" (syntax-e #'sym) s)))
(struct-field-info-list
 (syntax-local-value #'sym))
)])
#`(quote #,names))]))

 ;; This...
 (proc-names A)
 ;; Returns '(A-c A-b)

 (define-syntax (names-exist? stx)
   (syntax-case stx ()
 [(_ sym)
  (let ([names (map (λ (s)
  (string->symbol
   (format "~a-~a" (syntax-e #'sym) s)))
(struct-field-info-list
 (syntax-local-value #'sym))
)])
#`(andmap (λ (s)
(equal? 'lexical s))
  (map (λ (s)
 (defined? s))
   (quote #,names)))
)]))

 (names-exist? A)
 (names-exist? B)


 On Sat, Oct 30, 2021 at 10:33 PM Brian Beckman 
 wrote:

> Here are some of my latest (failed) experiments:
>
> #lang racket
>
> (requi

Re: [racket-users] How to discover a struct's interface without Dr Racket?

2021-10-31 Thread Brian Beckman
works :) after 'raco install struct-plus-plus'

tyvm

On Sunday, October 31, 2021 at 7:03:14 AM UTC-7 david@gmail.com wrote:

> The actual accessor functions are in there as well, not just the names.
>
> On Sun, Oct 31, 2021, 9:58 AM Jens Axel Søgaard  
> wrote:
>
>> A quick example:
>>
>> #lang racket
>> (require racket/require)
>> (require (filtered-in (λ (name) (regexp-replace #rx"struct[+][+]" name 
>> "struct"))
>>   struct-plus-plus))
>>
>> (struct horse (breed color legs))
>>
>> (define beauty (horse 'arabian 'black 4))
>>
>> (define info (force (struct-ref beauty)))
>> (map struct-field-name (struct-info-fields info))
>>
>> The result is:
>> '(breed color legs)
>>
>> Den søn. 31. okt. 2021 kl. 13.06 skrev David Storrs > >:
>>
>>>
>>>
>>> On Sun, Oct 31, 2021, 7:49 AM Jens Axel Søgaard  
>>> wrote:
>>>
 Hi Brian,

 A few random thoughts:

 > I would like, given only the symbol foo referring to the struct type 
 itself, 
 > to discover (at least) the list of procedures foo?, foo-a, foo-b, 
 plus 
 > anything else the author of foo (the type) wants me to see.

 When you want to look this up, is it in the repl (i.e. at runtime)?

 The standard `struct` construct doesn't store much reflection 
 information.
 Instead of fighting the standard construct, you can consider making a 
 little variation.

 If you are satisfied with having info for the structs defined in your 
 own program
 (i.e. modules you have written yourself), then you can consider making 
 a 
 module, say, `fancy-struct` that exports a macro where

(fancy-struct yada ...)

 expands into

(begin
   (fancy-struct yada ...)
   )

 Using `rename-out` you can export it as `struct`, so it can be used 
 without changing any existing code.

 /Jens Axel

>>>
>>> Coincidentally, that module exists!
>>>
>>>
>>> https://docs.racket-lang.org/struct-plus-plus/index.html#%28part._.Reflection%29
>>>
>>>
>>>


 Den søn. 31. okt. 2021 kl. 11.42 skrev Matt Jadud :

> Hi Brian,
>
> Does this help move you forward?
>
> It has been a while since I've stared at macros in Racket, so this 
> might be easier... 
>
> Also, make sure you're executing this code in a module. If you're 
> working in a REPL, I suspect all bets are off. It is certainly the case 
> that you could combine several of my exploration steps into a 
> simpler/cleaner macro, instead of generating lists of symbols, converting 
> them back to syntax objects, and so on.
>
> Also, as a solution/exploration, I... don't know how this would 
> interact with the full range of possible structs. Someone who knows more 
> about syntax and structs should be able to speak to how you'd find out 
> all 
> of the defined functions that spawn from struct definition/creation. (It 
> might also be useful to know *why* you want to destructure structs this 
> way? Knowing that may illuminate some other path forward.)
>
> #lang racket
> (require racket/struct-info)
>
> (struct A (b c))
>
> (struct B (e f) #:transparent)
>
> (require (for-syntax racket/struct-info))
> (define-syntax (get-field-names stx)
>   (syntax-case stx ()
> [(_ sym)
>  #`(quote
> #,(struct-field-info-list
>(syntax-local-value #'sym)))
>   ]))
>
> ;; These let me see the field names
> (get-field-names A)
> ;; Returns '(c b)
> (get-field-names B)
> ;; Returns '(f e)
>
> ;; 
> https://stackoverflow.com/questions/20076868/how-to-know-whether-a-racket-variable-is-defined-or-not
> (define-syntax (defined? stx)
>   (syntax-case stx ()
> [(_ id)
>  (with-syntax ([v (identifier-binding #'id)])
>#''v)]))
>
> (define-syntax (proc-names stx)
>   (syntax-case stx ()
> [(_ sym)
>  (let ([names (map (λ (s)
>  (string->symbol
>   (format "~a-~a" (syntax-e #'sym) s)))
>(struct-field-info-list
> (syntax-local-value #'sym))
>)])
>#`(quote #,names))]))
>
> ;; This...
> (proc-names A)
> ;; Returns '(A-c A-b)
>
> (define-syntax (names-exist? stx)
>   (syntax-case stx ()
> [(_ sym)
>  (let ([names (map (λ (s)
>  (string->symbol
>   (format "~a-~a" (syntax-e #'sym) s)))
>(struct-field-info-list
> (syntax-local-value #'sym))
>)])
>#`(andmap (λ (s)
>(equal? 'lexical s))
>  (map (λ (s)
>   

Re: [racket-users] How to discover a struct's interface without Dr Racket?

2021-10-31 Thread Brian Beckman
Hi, Matt ... I'll try your ideas in a little while. 

Regarding "why," I want the ability, from a module or a REPL, to quickly 
dump the attributes of an instance without having to look things up. The 
need arose when I was barnstorming and trying to explain syntax objects to 
someone, and he asked "what are the attributes of a syntax object?" I 
replied, "let's just dump one out," and that turned out impossible. So we 
did an F1 lookup of the doc and were confronted with the general 
meta-syntactic definition 
file:///usr/share/doc/racket/reference/stx-patterns.html#%28form._%28%28lib._racket%2Fprivate%2Fstxcase-scheme..rkt%29._syntax%29%29.
 
Well, we weren't going to finish understanding that in the one-hour lunch 
meeting we had.

Bottom line, I was unable to give a quick answer to a reasonable question.

On Sunday, October 31, 2021 at 3:42:19 AM UTC-7 Matt Jadud wrote:

> Hi Brian,
>
> Does this help move you forward?
>
> It has been a while since I've stared at macros in Racket, so this might 
> be easier... 
>
> Also, make sure you're executing this code in a module. If you're working 
> in a REPL, I suspect all bets are off. It is certainly the case that you 
> could combine several of my exploration steps into a simpler/cleaner macro, 
> instead of generating lists of symbols, converting them back to syntax 
> objects, and so on.
>
> Also, as a solution/exploration, I... don't know how this would interact 
> with the full range of possible structs. Someone who knows more about 
> syntax and structs should be able to speak to how you'd find out all of the 
> defined functions that spawn from struct definition/creation. (It might 
> also be useful to know *why* you want to destructure structs this way? 
> Knowing that may illuminate some other path forward.)
>
> #lang racket
> (require racket/struct-info)
>
> (struct A (b c))
>
> (struct B (e f) #:transparent)
>
> (require (for-syntax racket/struct-info))
> (define-syntax (get-field-names stx)
>   (syntax-case stx ()
> [(_ sym)
>  #`(quote
> #,(struct-field-info-list
>(syntax-local-value #'sym)))
>   ]))
>
> ;; These let me see the field names
> (get-field-names A)
> ;; Returns '(c b)
> (get-field-names B)
> ;; Returns '(f e)
>
> ;; 
> https://stackoverflow.com/questions/20076868/how-to-know-whether-a-racket-variable-is-defined-or-not
> (define-syntax (defined? stx)
>   (syntax-case stx ()
> [(_ id)
>  (with-syntax ([v (identifier-binding #'id)])
>#''v)]))
>
> (define-syntax (proc-names stx)
>   (syntax-case stx ()
> [(_ sym)
>  (let ([names (map (λ (s)
>  (string->symbol
>   (format "~a-~a" (syntax-e #'sym) s)))
>(struct-field-info-list
> (syntax-local-value #'sym))
>)])
>#`(quote #,names))]))
>
> ;; This...
> (proc-names A)
> ;; Returns '(A-c A-b)
>
> (define-syntax (names-exist? stx)
>   (syntax-case stx ()
> [(_ sym)
>  (let ([names (map (λ (s)
>  (string->symbol
>   (format "~a-~a" (syntax-e #'sym) s)))
>(struct-field-info-list
> (syntax-local-value #'sym))
>)])
>#`(andmap (λ (s)
>(equal? 'lexical s))
>  (map (λ (s)
> (defined? s))
>   (quote #,names)))
>)]))
>
> (names-exist? A)
> (names-exist? B)
>
>
> On Sat, Oct 30, 2021 at 10:33 PM Brian Beckman  wrote:
>
>> Here are some of my latest (failed) experiments:
>>
>> #lang racket
>>
>> (require (for-syntax racket/struct-info))
>> (require racket/pretty)
>>
>> (struct foo (a b) #:transparent)
>>
>> (displayln `("a foo object is transparent: I can see inside: \n  
>> (struct->vector (foo 1 2)) ~~> "
>>  ,(struct->vector (foo 1 2
>>
>> (displayln `("syntax object is opaque I can't see inside: \n  
>> (struct->vector #'foo) ~~> "
>>  ,(struct->vector #'foo)))
>>
>> ;;; Why do two copies of the syntax display? (One copy
>> ;;; is a side-effect. The other is a result).
>>
>> ;;; At expansion time, I can get some graphics in Dr-Racket for
>> ;;; definition of foo, but I cannot get likewise 
>> ;;; not into the definition of syntax. 
>> (begin-for-syntax
>>   (displayln 
>>(extract-struct-info
>> (syntax-local-value
>>  #'foo  ; #'syntax
>>
>> ;;; But the access procedures for #'syntax are known!?!? (I just
>> ;;; happen to know that there is a procedure named 'syntax-position';
>> ;;; my whole issue is in trying to find out the list of all
>> ;;; procedures defined in the system when the syntax type is created!)
>>
>> (syntax-position #'42)
>>
>> ;;; Whereas #'foo is known in this module scope,
>> ;;; (syntax struct:foo) is not known! Looks like the shorthand
>> ;;; #'whatever for making a syntax object is known, but the longhand,
>> ;;; presumab

Re: [racket-users] How to discover a struct's interface without Dr Racket?

2021-10-31 Thread Matt Jadud
Hi Brian,

In some ways, you did get a very good answer to your first question. You
were able to see the properties of a *syntax object*. But syntax objects
were, I think, only part of the picture you were looking for.

The questions "what does the *struct* form in Racket do, what bindings does
it introduce into the namespace, at what point in the macro-expansion tower
do those things happen, and how can I understand the mechanisms that are at
work in that expansion?" are... different questions, as you discovered.

If you're keen to understand the Racket macro system (not knowing your
background; apologies if this is all old news):

* Matthew B's *Beautiful Racket* has a nice section on Macros:
https://beautifulracket.com/explainer/macros.html
* Flatt's *Let's Build a Hygenic Macro Expander *will provide a conceptual
foundation that aligns with Racket's macro expander:
https://www.youtube.com/watch?v=Or_yKiI3Ha4
* Hendershott's *Fear of Macros *has an intimidating cat, and dives deeper
into the Racket tools of macro construction:
https://www.greghendershott.com/fear-of-macros/
* Clinger and Wand's *Hygenic Macro Technology* is a brief (100p) walk
through the history of macro expansion systems in the Scheme world:
https://dl.acm.org/doi/pdf/10.1145/3386330

These materials (in particular, Matthew's talk) might help give a sense for
what is involved in pulling back the curtain on a macro expansion, and the
kind of implementation details that are going on under the hood.

I would say that studying the code for *struct-plus-plus* could also be
informative, as it would provide a way to see how a struct system that
provides the kind of visibility you were looking for achieves that
visibility, and how it interacts with the macro expansion tower.

Cheers,
Matt


On Sun, Oct 31, 2021 at 11:52 AM Brian Beckman  wrote:

> Hi, Matt ... I'll try your ideas in a little while.
>
> Regarding "why," I want the ability, from a module or a REPL, to quickly
> dump the attributes of an instance without having to look things up. The
> need arose when I was barnstorming and trying to explain syntax objects to
> someone, and he asked "what are the attributes of a syntax object?" I
> replied, "let's just dump one out," and that turned out impossible. So we
> did an F1 lookup of the doc and were confronted with the general
> meta-syntactic definition
> file:///usr/share/doc/racket/reference/stx-patterns.html#%28form._%28%28lib._racket%2Fprivate%2Fstxcase-scheme..rkt%29._syntax%29%29.
> Well, we weren't going to finish understanding that in the one-hour lunch
> meeting we had.
>
> Bottom line, I was unable to give a quick answer to a reasonable question.
>
> On Sunday, October 31, 2021 at 3:42:19 AM UTC-7 Matt Jadud wrote:
>
>> Hi Brian,
>>
>> Does this help move you forward?
>>
>> It has been a while since I've stared at macros in Racket, so this might
>> be easier...
>>
>> Also, make sure you're executing this code in a module. If you're working
>> in a REPL, I suspect all bets are off. It is certainly the case that you
>> could combine several of my exploration steps into a simpler/cleaner macro,
>> instead of generating lists of symbols, converting them back to syntax
>> objects, and so on.
>>
>> Also, as a solution/exploration, I... don't know how this would interact
>> with the full range of possible structs. Someone who knows more about
>> syntax and structs should be able to speak to how you'd find out all of the
>> defined functions that spawn from struct definition/creation. (It might
>> also be useful to know *why* you want to destructure structs this way?
>> Knowing that may illuminate some other path forward.)
>>
>> #lang racket
>> (require racket/struct-info)
>>
>> (struct A (b c))
>>
>> (struct B (e f) #:transparent)
>>
>> (require (for-syntax racket/struct-info))
>> (define-syntax (get-field-names stx)
>>   (syntax-case stx ()
>> [(_ sym)
>>  #`(quote
>> #,(struct-field-info-list
>>(syntax-local-value #'sym)))
>>   ]))
>>
>> ;; These let me see the field names
>> (get-field-names A)
>> ;; Returns '(c b)
>> (get-field-names B)
>> ;; Returns '(f e)
>>
>> ;;
>> https://stackoverflow.com/questions/20076868/how-to-know-whether-a-racket-variable-is-defined-or-not
>> (define-syntax (defined? stx)
>>   (syntax-case stx ()
>> [(_ id)
>>  (with-syntax ([v (identifier-binding #'id)])
>>#''v)]))
>>
>> (define-syntax (proc-names stx)
>>   (syntax-case stx ()
>> [(_ sym)
>>  (let ([names (map (λ (s)
>>  (string->symbol
>>   (format "~a-~a" (syntax-e #'sym) s)))
>>(struct-field-info-list
>> (syntax-local-value #'sym))
>>)])
>>#`(quote #,names))]))
>>
>> ;; This...
>> (proc-names A)
>> ;; Returns '(A-c A-b)
>>
>> (define-syntax (names-exist? stx)
>>   (syntax-case stx ()
>> [(_ sym)
>>  (let ([names (map (λ (s)
>>   

Re: [racket-users] How to discover a struct's interface without Dr Racket?

2021-10-31 Thread Brian Beckman
Thanks very much, Matt. This is helpful. 

I understand macros in a general way (I'm an old [very old] Scheme hand, 
plus I use Mathematica every day, and it's almost nothing but macros). 
However, the particulars of Racket's hygienic macro system are new to me, 
and I will read-up on all the references you sent. 

Once again, thanks very much for your kind attention and generous expense 
of time. I'm doing a lot of barnstorming (using educated guesswork) in 
trying to build stuff quickly, and targeted, bottom-up reading such as you 
suggest is very a-propos and helpful at quick-starting me and my team. 
Racket got very big, but in a good way, since I last looked at it 20 years 
ago.

On Sunday, October 31, 2021 at 9:59:58 AM UTC-7 Matt Jadud wrote:

> Hi Brian,
>
> In some ways, you did get a very good answer to your first question. You 
> were able to see the properties of a *syntax object*. But syntax objects 
> were, I think, only part of the picture you were looking for.
>
> The questions "what does the *struct* form in Racket do, what bindings 
> does it introduce into the namespace, at what point in the macro-expansion 
> tower do those things happen, and how can I understand the mechanisms that 
> are at work in that expansion?" are... different questions, as you 
> discovered.
>
> If you're keen to understand the Racket macro system (not knowing your 
> background; apologies if this is all old news):
>
> * Matthew B's *Beautiful Racket* has a nice section on Macros: 
> https://beautifulracket.com/explainer/macros.html
> * Flatt's *Let's Build a Hygenic Macro Expander *will provide a 
> conceptual foundation that aligns with Racket's macro expander: 
> https://www.youtube.com/watch?v=Or_yKiI3Ha4
> * Hendershott's *Fear of Macros *has an intimidating cat, and dives 
> deeper into the Racket tools of macro construction: 
> https://www.greghendershott.com/fear-of-macros/
> * Clinger and Wand's *Hygenic Macro Technology* is a brief (100p) walk 
> through the history of macro expansion systems in the Scheme world: 
> https://dl.acm.org/doi/pdf/10.1145/3386330
>
> These materials (in particular, Matthew's talk) might help give a sense 
> for what is involved in pulling back the curtain on a macro expansion, and 
> the kind of implementation details that are going on under the hood.
>
> I would say that studying the code for *struct-plus-plus* could also be 
> informative, as it would provide a way to see how a struct system that 
> provides the kind of visibility you were looking for achieves that 
> visibility, and how it interacts with the macro expansion tower.
>
> Cheers,
> Matt
>
>
> On Sun, Oct 31, 2021 at 11:52 AM Brian Beckman  wrote:
>
>> Hi, Matt ... I'll try your ideas in a little while. 
>>
>> Regarding "why," I want the ability, from a module or a REPL, to quickly 
>> dump the attributes of an instance without having to look things up. The 
>> need arose when I was barnstorming and trying to explain syntax objects to 
>> someone, and he asked "what are the attributes of a syntax object?" I 
>> replied, "let's just dump one out," and that turned out impossible. So we 
>> did an F1 lookup of the doc and were confronted with the general 
>> meta-syntactic definition 
>> file:///usr/share/doc/racket/reference/stx-patterns.html#%28form._%28%28lib._racket%2Fprivate%2Fstxcase-scheme..rkt%29._syntax%29%29.
>>  
>> Well, we weren't going to finish understanding that in the one-hour lunch 
>> meeting we had.
>>
>> Bottom line, I was unable to give a quick answer to a reasonable question.
>>
>> On Sunday, October 31, 2021 at 3:42:19 AM UTC-7 Matt Jadud wrote:
>>
>>> Hi Brian,
>>>
>>> Does this help move you forward?
>>>
>>> It has been a while since I've stared at macros in Racket, so this might 
>>> be easier... 
>>>
>>> Also, make sure you're executing this code in a module. If you're 
>>> working in a REPL, I suspect all bets are off. It is certainly the case 
>>> that you could combine several of my exploration steps into a 
>>> simpler/cleaner macro, instead of generating lists of symbols, converting 
>>> them back to syntax objects, and so on.
>>>
>>> Also, as a solution/exploration, I... don't know how this would interact 
>>> with the full range of possible structs. Someone who knows more about 
>>> syntax and structs should be able to speak to how you'd find out all of the 
>>> defined functions that spawn from struct definition/creation. (It might 
>>> also be useful to know *why* you want to destructure structs this way? 
>>> Knowing that may illuminate some other path forward.)
>>>
>>> #lang racket
>>> (require racket/struct-info)
>>>
>>> (struct A (b c))
>>>
>>> (struct B (e f) #:transparent)
>>>
>>> (require (for-syntax racket/struct-info))
>>> (define-syntax (get-field-names stx)
>>>   (syntax-case stx ()
>>> [(_ sym)
>>>  #`(quote
>>> #,(struct-field-info-list
>>>(syntax-local-value #'sym)))
>>>   ]))
>>>
>>> ;; These let me see the field names
>>