OK, I hope you can see the difference though between that and what I
showed.
Of course I can; I'm just illustrating a point by exaggeration.
They are not the same; in your example:
- It's not clear what the magic symbols are
- The user does not specify the magic symbols (as they did in mine)
It's not clear in the case of multiple packages or namespaces. (In
which package does "name" get interned? It depends on *when* the
string is interned, because that decides the enclosing scope. Or does
newLISP not have packages?)
Neither are the names specified in a query such as "SELECT * FROM
people". Who knows what'll happen when you do "SELECT p1.name ...".
You're about half-way to complete anaphora when you're starting to
pull symbol names out of syntax-laden strings (or databases). That's
magic, at least when compared to ordinary lexical symbol reference.
Given that there's little to no advantage to doing this, I don't see
the point.
This sort of programming style is easy to abuse and can sometimes
lead to confusion if handled incorrectly, but when applied in the
appropriate manner it can be extremely useful.
The 'for-query-with-db' function is a good example of doing this
correctly because it:
- Documents its behavior
- Creates symbols based on user input, not of its own accord as in
your example
- Clearly distinguishes them through a special naming convention
- Has advantages over other forms of solving the same problem
... and it's a bad example, because it:
- Quietly and maybe accidentally shadows variables from enclosing scopes
- Fails to nest queries which share names
- Silently interns new variable names in your packages
- Uses eval (which apparently is fine in newLISP, but as a Common
Lisper and Clojurite strikes me as pointless)
- etc.
I see no point in doing this rather than going the conventional macro
route. c.c.sql, for example, would do this:
(with-query-results res
["SELECT name FROM people"]
(println (:name res)))
-- res is a map. You can pass it around, access its values, and your
own function `name` doesn't get shadowed by your query.
c.c.sql also allows you to synthesize queries from Lisp forms, which I
think is more useful than trying to extract symbol names from a SQL
string.
The macroexpansion occurs at compile time. If you have all the
knowledge at compile time, you can do the work then. If you don't,
the macro has to expand into code that does the work at runtime.
Thanks for the example and explanation!
Sure thing!
--
You received this message because you are subscribed to the Google
Groups "Clojure" group.
To post to this group, send email to clojure@googlegroups.com
Note that posts from new members are moderated - please be patient with your
first post.
To unsubscribe from this group, send email to
clojure+unsubscr...@googlegroups.com
For more options, visit this group at
http://groups.google.com/group/clojure?hl=en