4 ms·
Finally read the reference on lisp reader macros : http://www.lispworks.com/documentation/HyperSpec/Front/X_Mast_9.htm http://www.lispworks.com/documentation/Hy
by naveen99 6y ago
Finally read the reference on lisp reader macros : http://www.lispworks.com/documentation/HyperSpec/Front/X_Mast_9.htm http://www.lispworks.com/documentation/HyperSpec/Front/X_Mas...
Now I sort of get what #+unix means...
- reikonomusha 6y ago#+foo A B This says if the Lisp supports “foo” as a “feature” (a precise term in Common Lisp), the A will be included. Otherwise A will be treated as a comment. B will be included regardless. It’s roughly equivalent to #ifdef foo A #endif B The opposite is #-. #-unix A B is roughly #ifndef unix A #endif B So you can write portable source code this way. (defvar path-separator #+unix "/" #+windows "\\" #-(or unix windows) (error "idk")) This will define a variable called PATH-SEPARATOR which is / for UNIX, \ for Windows, and a compile-time error otherwise. The rabbit hole goes deep on this. There’s a reason it uses ‘#’, and as you pointed out, it has to do with built-in (dispatching) reader macros.
- lisper 6y ago#+ is only one of many, many standard reader macros (as you can see from that link). You can also define your own, which makes Lisp syntax almost infinitely malleable. For example, it's possible to change the Lisp reader so that it natively reads infix syntax. See: http://flownet.com/ron/lisp/djbec.lisp http://flownet.com/ron/lisp/djbec.lisp for an example. Scroll down to the definition of xpt-add.
- jlarocco 6y agoFor the benefit of everybody else, #+ does feature checking. The Common Lisp standard defines a standard "special variable" (kind of like a global) named * features * (shouldn't be spaces, but HN italicizes it otherwise), and #+ (and #-) take a "feature expression" and conditionally execute the expression that immediately follows it when the feature expression is true. If the feature check is false, the next expression is ignored. For example: #+freebsd(print "This is FreeBSD") #+(not (and 64-bit linux))(print "This is not 64-bit Linux.") #+quicklisp (ql:quickload :some-library) The CL standard lists a few standard features (:common-lisp, :ieee-floating-point, etc.) but for the most part implementations and libraries define their own. It's not perfect, but works well enough in practice.
- TeMPOraL 6y agoThe common thing done with it is: #+nil(this expression (won't be read)) (Also done with #+and, and #+or.) This is an unofficial Common Lisp s-expression level comment. One of these incredibly nice things that's missing in most programming languages. It comments out a single s-expression, no matter how complex. It's like a #|block comment|# in that it can span multiple lines, and like ; line comment in that you only put something at the beginning. Have a complex expression within a function, that you need to temporarily shut down? Just shove #+nil in front of it. (The #+nil version is discouragd because there's a remote chance somebody will define a * feature * called :nil for some reason.) A less-common thing done with it is library interop. Many libraries tend to add a tag to * features * to indicate they've been loaded, so in your library, you can use #+library_tag to detect that another library is a part of the same project, and conditionally compile-in some extensions or interoperability code. (@dang, I think HN could use a way to escape the * * formatting marks. For a site and community that has a soft spot for Lisp, not being able to type in the "earmuffs" is something that always bewildered me.)
- gumby 6y agoThe important thing about reader macros is that they happen at read time. It causes code to be executed at tokenizing time (so you can make your own syntax, e.g. #{ ... } could return a JSON object directly) even before evaluation or macroexpansion. So #+ and #- really only scratch the surface. Someone wrote a comment about using #+ to define the path delimiter (/ or \), but that is something that could be looked up at runtime. Read-time extension is unusual in programming languages (C++ has such a feature for a more limited set of cases).