On Sun, Sep 25, 2016 at 3:34 AM, William G Hatch <will...@hatch.uno> wrote: > First of all, I really didn't mean any offense. I think the at-reader > and my nestable string delimiters are trying to solve slightly > different problems, and I didn't really convey that well. I didn't > mean for it to be "Eli bait". Let me explain my use case a little, > and maybe my earlier mail will seem less baiting in the context I had > intended, albeit poorly communicated.
To be clear, no offense taken -- I'm only considering the technical reasons to want yet another string delimiter and the technical aspects of what you get. "Eli bait" is not because I take it personally, it's just because I spent a ton of time thinking about such problems, and I'd hate to see people fall into the expected traps when following "traditional" solutions, not seeing how the @-syntax already provides a nice solution. (I suspected that you'd fall into them, and later in this email you indeed do...) > So I really do just mean that the string delimiters themselves nest -- > IE it balances them so that the string doesn't necessarily end once it > hits an ending delimiter. So yes, any two characters will do for the > job. That in itself is something that I've wanted independent of > anything else, so for me that was a good enough reason to make this, > and is something that I'll use it for, to avoid things like \", which > have always irked me (whether or not it's reasonable that that should > bother me). Note that the scribble syntax starts with that as a basic feature. That is, if you replace {}s with something else like «», then inside a quoted context @«...» any matching «»s are ignored. > Basically, I want to have a macro that will be fully in charge of > determining the meaning of the string, and I want to be able to use > the same reader functions in the macro that I use in the #lang. Same here: this is one of the uses cases I described many times for the scribble syntax: start with a macro that uses a parser to parse the whole thing, then refine by making it parse just one form and start besting @-forms, and eventually get to a point when you have a new #lang implementation. > But to use the same read-syntax function that my language uses, I need > a port to run it on. To make this port, I really just need a string > with no pre-read syntax objects inside it. So in this case I don't > want the top-level reader of whatever #lang I'm in to look in the > string, I just want the macro to be able to use read-syntax on the > full string. Yes, and you can do all of that with just a string, which you can still get from an @-form -- just throw a syntax error if it's not all strings. And with just that you get the *benefit* of ignoring indentation which makes it possible to use your syntax in a sane way. > If the middle of the string has already been read into syntax objects, > my reader functions would be much more complicated to write (IE I'd > have to figure out how to deal with the port ending in the middle of a > parenthesised expression or something, then use a pre-read syntax > object, then jump back into reading the next section that remained a > string while conveying whatever context I was in in the last string > segment...). Right -- that's what I mentioned as "throw a syntax error" above. But it would be a good idea to think about why it's a syntax error, which would in most cases get you closer to something that is a composable language. > And the string splitting, which is as you've shown quite helpful in > many cases, would in this case simply be something that I would have > to undo, which as you point out would be a bit of a waste. What I view as a waste is not just undoing the indentation elimination -- it's the idea of a form where you want indentation to matter at the semantic runtime level. To clarify, my opinion is that (foo bar baz) and (foo bar baz) should be the same. @-expressions follow that; (traditional) here-strings do not. Because here-strings do not follow that, you end up writing ugly code like (foo #<<FOO blah FOO baz) which is a mess that might make your readers' eyes bleed. The usual shell-way-out is to just use it in a context that is insensitive for spaces so you end up writing (foo #<<FOO blah FOO baz) and hope that `foo` will overlook the spaces that are all still there. > So I see the difference as being that in uses like scribble, the bold > procedure isn't trying to use a reader on its arguments, and the > at-reader needs to have split them up and turned the nested > expressions into s-expressions already for them to have their intended > meaning. *Don't* confuse scribble-the-documentation-system with the syntax -- the syntax is useful for many other cases, and designed to make sense in other cases. See my description (specifically section 4, which is very relevant here), and the scribble/text and scribble/html languages. > [...] > ;; So basically the rash macro does exactly the same thing as #lang > ;; rash, but is embeddable in #lang whatever! Yes, and you can get the same with any string, and (rash "stuff in a different language") The next problem is quoting and backslash hell, so you want a better quotation, and (I'm guessing) you end up with something like (rash «stuff in a different language») using @-forms would be a tiny delta for the implementation -- basically just a string-append (actually, not even a delta since your macro already allows multiple strings), and the use is more convenient: @rash{stuff in a different language} > each one can do the reading however it sees fit, as long as at each > level I can pass an appropriate string to the next level down. The only tricky bit here is that if you want to deal with only strings and at the same time maintain a syntax-time parsing of strings, then you need to do this whole multi-level collapsing as a macro thing, which means no runtime expressions. > Maybe the languages have very different views on which characters do > something special (or specifically should not do something special), > including flag characters like @ (or any one you choose at the top > level or a higher level up in the nesting). Note that the scribble syntax uses "@" by default, but it's easy to change, as Matthew B. did with pollen. > For example, something like this could happen: > > (define some-output > (rash/out > «some-query $(first > (python-ish-list-comprehend > «machine for i in machine-list where should-i-query(i)»)) > $(make-query > «this is a bogus example that I'm really stretching > for, but maybe this is some nice syntax for some > sort of query producing dsl? And maybe it has some > macro in it in whatever its syntax is to > (go-a-level-deeper «in this nonsense ...») > But importantly, no top-level reader has to know or > care what the syntax here is, nor the rash reader, > nor any reader in between, aside from simply > preserving it as a string, which I can hopefully do > in most any language.»)»)) And here you're falling into the trap I mentioned above. You're trying to use "$" as an escape, but, for example, what happens if you want to escape a single identifier and not an expression? Anyway, here's the same thing using the scribble syntax: (define some-output @rash/out{ some-query @(first @python-ish-list-comprehend{ machine for i in machine-list where should-i-query(i)}) @make-query{ this is a bogus example that I'm really stretching for, but maybe this is some nice syntax for some sort of query producing dsl? And maybe it has some macro in it in whatever its syntax is to (go-a-level-deeper {in this nonsense ...}) But importantly, no top-level reader has to know or care what the syntax here is, nor the rash reader, nor any reader in between, aside from simply preserving it as a string, which I can hopefully do in most any language.}}) Note that at the superficial concrete level what this does is (a) eliminates the need for some "$" escape character, and (b) reduces the double-delimiter (foo «...») that you often use into a single delimiter form of @foo{...}. This latter point is subtly important: users that write your version need to be aware of both sexpr syntax and string syntax and how they combine, whereas users that write my version have a single delimiter. This is combined with the fact that "@" means the same at all level in the scribble syntax -- that simplifies things further by removing the need for some $-like escape construct for interpolation. These two features make it easier to comprehend the new thing as a new syntax rather than be aware of some places that are texts, some that are not, and the ways to combine this all in code. It might help to compare this with JS's "template literals", where the equivalent of the scribble form: @foo{... @bar{... @baz ...} ...} is possible to write -- it's even not that hard: just replace @X{_} with "${X(`_`)}" except at the toplevel: foo(`... ${bar(`... @{baz} ...`)} ...`) but given how obfuscated the result is (specifically: you now have three paired delimiters: {}s for interpolation, ()s for arguments, and ``s for text), almost nobody will actually write such code. Note also that in *both* of these cases you need to deal with the problem of `first` being a Racket runtime binding that gets used at the syntax level if you want to stick with `rash/out` doing its parsing as a macro implementation -- that's a problem that is inherently there regardless of concrete syntax. But the scribble syntax provides an easy way to handle this: you just need to define `rash/out` as a function (so do the parsing at runtime), and the result plays much nicer with any language it's used in. > I'm a little hard pressed to come up with examples I haven't thought > of remotely concretely yet, but it seems to me that it's much easier > to have these sort of #lang-embedding macros that do their own reading > if you just have a simple string. At this point I'm guessing that you'd still not be convinced. So maybe phrase this as a challenge: see if you can come up with an actual example where the scribble syntax won't do what you want, or examples that you're not sure how the scribble syntax would look like. Maybe doing this will lead to further enlightment. (Feel free to email me such examples off-list.) > I'm really sorry if my initial mail came off as offensive or > aggressive against the at-reader, because I really think it's great. > It's just that it doesn't seem to be the tool best suited to my > particular need, [...] I'm not trying to defend the scrible syntax's honor -- I'm only trying to show you why it solves your particular needs too... As a long postfix comment, the personal angle here is that I've been obsessed with such problems for a *very* long time. At some point I've had a system that I'm guessing would interest you: I've basically made a language where <<>> would delimit meta-level text to be run and its output used instead, then I made it so each of these could specify its own language so something like <<TCL: ...>> would run in a tcl interpreter (it was before python became popular), and you could nest any number of levels (using a different language in each). I've used some shreds of that years later in mzpp which is a much more simplistic language, and closer to a traditional template system. And since you've mentioned changing the "@" character at every level, I've also implemented something on that side of the spectrum -- mztext -- where the resulting language is more tex-like where you can do arbitrary parsing at each nested level down to changing how "functions" are written and arguments are parsed, and (just like tex) the result is pretty powerful in what it can do, but nobody ever needs that complication which makes the whole thing useless for practical purposes. The scribble syntax is the last thing I had in that long list of experiments which finally made sense at all levels, and was both something that was easy to understand yet flexible to express any of the complicated needs. -- ((x=>x(x))(x=>x(x))) Eli Barzilay: http://barzilay.org/ Maze is Life! -- 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. For more options, visit https://groups.google.com/d/optout.