<html><head></head><body style="word-wrap: break-word; -webkit-nbsp-mode: space; -webkit-line-break: after-white-space; "><div>I guess I would like to hear more about why adding an Objective-C like syntax to Lisp is a good thing. No flame war please, I am not saying that there could be no good reason but I am not quite sold. As many of you know Lisp itself is not generally considered a great programming language from a syntactic point of view due to parenthesis paranoia. However, if I would be asked to point to one programming language disliked by todays students even more it actually would be Objective-C. BUT, the students do use Objective-C + Cocoa because they can make cool iOS apps, e.g., games they can actually make money with, IN SPITE of the Objective-C syntax not thanks to it. </div><div><br></div><div>Alex</div><div><br></div><br><div><div>On Dec 22, 2010, at 8:28 AM, Pascal J. Bourguignon wrote:</div><br class="Apple-interchange-newline"><blockquote type="cite"><div>Hello,<br><br>I've been writing a couple of reader macro to implement an<br>Objective-Clike syntax for Common Lisp, above the ccl Objective-C<br>bridge.<br><br>I still have finalize the processing of type specifiers (I need to learn<br>more about ccl FFI types), however here is already the documentation<br>source.<br><br>You may find a snapshot tarball at <br><a href="ftp://ftp.informatimago.com/users/pjb/lisp/objcl.tar.bz2">ftp://ftp.informatimago.com/users/pjb/lisp/objcl.tar.bz2</a><br>with the sources and the PDF of the documentation.<br><br><br>Eventually, it would be nice if this was distributed with ccl, as a<br>contribution (for now it's under GPL2, but I would provide any required<br>license for integration with ccl).<br><br>I'd gladly read any comment about it.<br><br>------------------------------------------------------------------------<br>.. comment: -*- mode:rst; coding:utf-8; -*-<br><br>Objective-CL<br>############<br><br>Objective-Clike syntax for Common Lisp<br>=======================================<br><br>Bugs<br>----<br><br>The ``type-specifiers`` are not defined yet. I need to learn about<br>``ccl`` FFI and perhaps add a syntax, or at least improve the reading<br>of ``type-specifiers``. Notably, for now they're merely read in the<br>keyword package so we cannot give type specifiers such as: (NSRect) or<br>(NSWindow*).<br><br><br>Motivation<br>----------<br><br>The purpose of this package is to provide a few reader macros<br>implementing a syntax like Objective-C to program with Objective-C FFI<br>such as the ``ccl`` Objective-C bridge.<br><br>The principles of the Objective-C syntax is that it is a small set of<br>extensions over the syntax of the base language (C in the case of<br>Objective-C). Namely:<br><br>- message sending expressions are put inside brackets (inspired from<br> Smalltalk block notation), and have basically the Smalltalk message<br> sending syntax.<br><br>- class declarations and definitions (interface and implementation)<br> and other Objective-C specific elements use keywords prefixed by the<br> #\\@ character.<br><br><br>The later is a little at odd with lisp nature, where every form is an<br>expression, and where parenthesized syntax is prefered. We will<br>therefore provide a more Smalltalk-like way to define classes and<br>methods (while retaining the #\\@ character as prefix for some<br>symbols, and as a reader macro to read Objective-C string literals).<br><br><br>Principles<br>----------<br><br>Two reader macros are provided:<br><br>- a reader macro bound to #\\[ is used to parse message sending<br> expressions, just like in Objective-C, but since the underlying<br> language is lisp, sub-expressions starting with parentheses are read<br> just like normal sexps (they may further contain Objective-CL syntax).<br><br>- a reader macro bound to #\\@ which is used to read:<br><br> - an Objective-C literal strings when followed by a double-quote<br> starting a lisp string.<br><br> - a class or method definition expression, when followed by an<br> opening bracket #\\[. The syntax used for these definition<br> expression is similar to the message sending syntax, but it's<br> processed more like a special operator or macro than a real<br> message sending: the sub-expression are evaluated with different<br> rules that depend on the operation. It's called a pseudo-message.<br><br> - a normal lisp symbol otherwise.<br><br>¶<br><br>These reader macros expand to normal lisp forms, using symbols<br>exported from a portability layer package, nicknamed OCLO, which<br>should be implemented specifically for each Objective-C bridge or FFI.<br>The implementation of this bridge is out of scope of these syntax-<br>providing reader macros.<br><br><br>Message Sending<br>---------------<br><br>The syntax is: ::<br><br> objcl-message-expr := '[' message-send ']' .<br><br> message-send := recipient message .<br> recipient := sexp | class-name | 'super' | 'self' .<br> class-name := objcl-identifier .<br><br> message := simple-selector | compound-selector final-arguments .<br><br> simple-selector := objcl-identifier .<br> compound-selector := objcl-identifier ':' sexp compound-selector<br> | objcl-identifier ':' sexp .<br> final-arguments := | '(' type-identifier ')' sexp final-arguments .<br> type-identifier := symbol .<br><br><br> -- FIXME type-identifier; perhaps we need:<br> -- type-identifier := symbol | symbol sexp .<br> -- for example: (char *)cString (array (int 10))tenInts ?<br> -- Check with what is available at the FFI/bridge level.<br><br><br>An ``objcl-identifier`` is a case sensitive identifier that is converted<br>to a lisp symbol according to the rules of Objective-C to Common Lisp<br>identifier translation.<br><br>A ``sexp`` is a normal lisp expression, which might be another message<br>sending bracketed expression (or another Objective-CL form).<br><br>There should be no space between the ``objcl-identifier`` and the colon.<br>After the first ``objcl-identifier`` in a compound-selector, the<br>remaining ``objcl-identifiers`` can be absent, in which case the colon<br>must be separated from the previous expression by a space.<br><br><br>When recipient is ``super``, an ``(oclo:send-super self ...)`` form is returned.<br>FIXME document the other forms returned.<br><br>Examples: ::<br><br> [self update]<br><br> [window orderFront:sender]<br><br> [array performSelector:(@selector "drawRect:") withObject:rect]<br><br> (let ((o [[NSObject alloc] init])) <br> [NSArray arrayWithObjects:o (id)o (id)o (id)nil])<br><br><br> '[array performSelector:(@selector "drawRect:") withObject:rect]<br> → (OBJC:SEND ARRAY :PERFORM-SELECTOR (@SELECTOR "drawRect:") :WITH-OBJECT RECT)<br><br>Class definition<br>----------------<br><br>Classes are created by sending a ``subClass:slots:`` pseudo-message to its superclass.<br><br>The syntax is : ::<br><br> objcl-definition := '@[' class-definition | instance-method-definition | class-method-definition ']' .<br><br> class-definition := super-class-name 'subClass:' class-name 'slots:' '(' slots ')' .<br><br> class-name := objcl-identifier .<br> super-class-name := objcl-identifier .<br> slots := | slot slots .<br> slot := lisp-slot | objcl-slot .<br> lisp-slot := slot-specifier . -- see clhs defclass.<br><br><br> -- objcl-slot := ... -- not defined yet. <br> -- We'd want some simplified definition, and using Obj-C names.<br><br><br>Examples: ::<br><br> @[NSObject subClass:SpaceShip<br> slots:((position :accessor ship-position :initform (make-position))<br> (speed :accessor ship-speed :initform 0.0))]<br><br><br>Method definition<br>-----------------<br><br>Class and instance methods are defined by sending a pseudo-message to<br>the class, either ``method:resultType:body:`` to create an instance<br>method, or ``classMethod:resultType:body:`` to create a class method.<br><br><br>The syntax is : ::<br><br> objcl-definition := '@[' class-definition | instance-method-definition | class-method-definition ']' .<br><br> instance-method-definition := class-name 'method:' '(' signature ')'<br> 'resultType:' '(' type-identifier ')'<br> 'body:' body .<br><br> class-method-definition := class-name 'classMethod:' '(' signature ')'<br> 'resultType:' '(' type-identifier ')'<br> 'body:' body .<br><br> class-name := objcl-identifier .<br> signature := simple-signature | compound-signature final-signature .<br> simple-signature := objcl-identifier .<br> compound-signature := objcl-identifier ':' '(' type-identifier ')' objcl-identifier compound-signature<br> | objcl-identifier ':' '(' type-identifier ')' objcl-identifier .<br> final-signature := '&rest' objcl-identifier .<br> body := | sexp body .<br><br> -- FIXME type-identifier; perhaps we need:<br> -- type-identifier := symbol | symbol sexp .<br> -- for example: (char *)cString (array (int 10))tenInts ?<br> -- Check with what is available at the FFI/bridge level.<br><br>There should be no space between the ``objcl-identifier`` and the colon.<br>After the first ``objcl-identifier`` in a compound-selector, the<br>remaining ``objcl-identifiers`` can be absent, in which case the colon<br>must be separated from the previous expression by a space.<br><br>Examples: ::<br><br> @[SpaceShip classMethod:(shipAtPosition:(Position)aPosition)<br> resultType:(id)<br> body:(let ((new-ship [[self alloc] init]))<br> [new-ship setPosition:aPosition]<br> new-ship)]<br><br> @[SpaceShip method:(moveToward:(Direction)aDirection atSpeed:(double)velocity)<br> resultType:(id)<br> body:(let ((new-pos [[self position] offset:...]))<br> (do-something new-pos)<br> [self setPosition:new-pos])]<br><br>String literals<br>---------------<br><br>The syntax read is: ::<br><br> objcl-string-literal := '@"' { character } '"' .<br><br>A CL string is read (ie. with the same escaping rules as normal CL<br>strings), and an (oclo:@ "string") form is returned.<br><br>Examples: ::<br><br> @"Untitled"<br> @"String with \"quotes\" and \\ backslash."<br> @"String with<br> new lines"<br><br><br><br><br><br>-- <br>__Pascal Bourguignon__ http://www.informatimago.com/<br>A bad day in () is better than a good day in {}.<br><br>_______________________________________________<br>Openmcl-devel mailing list<br>Openmcl-devel@clozure.com<br>http://clozure.com/mailman/listinfo/openmcl-devel<br></div></blockquote></div><br><div>
<span class="Apple-style-span" style="border-collapse: separate; color: rgb(0, 0, 0); font-family: Helvetica; font-size: 12px; font-style: normal; font-variant: normal; font-weight: normal; letter-spacing: normal; line-height: normal; orphans: 2; text-align: auto; text-indent: 0px; text-transform: none; white-space: normal; widows: 2; word-spacing: 0px; -webkit-border-horizontal-spacing: 0px; -webkit-border-vertical-spacing: 0px; -webkit-text-decorations-in-effect: none; -webkit-text-size-adjust: auto; -webkit-text-stroke-width: 0; "><span class="Apple-style-span" style="border-collapse: separate; border-spacing: 0px 0px; color: rgb(0, 0, 0); font-family: Helvetica; font-size: 12px; font-style: normal; font-variant: normal; font-weight: normal; letter-spacing: normal; line-height: normal; text-align: auto; -khtml-text-decorations-in-effect: none; text-indent: 0px; -apple-text-size-adjust: auto; text-transform: none; orphans: 2; white-space: normal; widows: 2; word-spacing: 0px; "><span class="Apple-style-span" style="border-collapse: separate; border-spacing: 0px 0px; color: rgb(0, 0, 0); font-family: Helvetica; font-size: 12px; font-style: normal; font-variant: normal; font-weight: normal; letter-spacing: normal; line-height: normal; text-align: auto; -khtml-text-decorations-in-effect: none; text-indent: 0px; -apple-text-size-adjust: auto; text-transform: none; orphans: 2; white-space: normal; widows: 2; word-spacing: 0px; "><span class="Apple-style-span" style="border-collapse: separate; border-spacing: 0px 0px; color: rgb(0, 0, 0); font-family: Helvetica; font-size: 12px; font-style: normal; font-variant: normal; font-weight: normal; letter-spacing: normal; line-height: normal; text-align: auto; -khtml-text-decorations-in-effect: none; text-indent: 0px; -apple-text-size-adjust: auto; text-transform: none; orphans: 2; white-space: normal; widows: 2; word-spacing: 0px; "><p style="margin: 0.0px 0.0px 0.0px 0.0px"><font face="Helvetica" size="3" style="font: 12.0px Helvetica">Prof. Alexander Repenning</font></p><p style="margin: 0.0px 0.0px 0.0px 0.0px"><br class="khtml-block-placeholder"></p><p style="margin: 0.0px 0.0px 0.0px 0.0px">University of Colorado</p><p style="margin: 0.0px 0.0px 0.0px 0.0px">Computer Science Department</p><p style="margin: 0.0px 0.0px 0.0px 0.0px">Boulder, CO 80309-430</p><p style="margin: 0.0px 0.0px 0.0px 0.0px"><br class="khtml-block-placeholder"></p><p style="margin: 0.0px 0.0px 0.0px 0.0px"><font face="Helvetica" size="3" style="font: 12.0px Helvetica">vCard: <a href="http://www.cs.colorado.edu/~ralex/AlexanderRepenning.vcf">http://www.cs.colorado.edu/~ralex/AlexanderRepenning.vcf</a></font></p><br class="Apple-interchange-newline"></span></span></span></span>
</div>
<br></body></html>