From 0e50007d98c6b507e71762d9e5d21b2ee9ec4886 Mon Sep 17 00:00:00 2001 From: Kaz Kylheku Date: Sat, 22 Feb 2014 19:30:40 -0800 Subject: * parser.y: Allow the (. expr) syntax to denote expr. * eval.h: Declare existing lambda_s extern variable. * lib.c (obj_print, obj_pprint): print (lambda sym ...) as (lambda (. sym) ...) and (lambda sym) as (lambda (. sym)). * txr.1: document it. --- ChangeLog | 11 +++++++++++ eval.h | 2 +- lib.c | 28 ++++++++++++++++++++++++++++ parser.y | 1 + txr.1 | 27 +++++++++++++++++++++++++++ 5 files changed, 68 insertions(+), 1 deletion(-) diff --git a/ChangeLog b/ChangeLog index 0286a61c..02f27206 100644 --- a/ChangeLog +++ b/ChangeLog @@ -1,3 +1,14 @@ +2014-02-22 Kaz Kylheku + + * parser.y: Allow the (. expr) syntax to denote expr. + + * eval.h: Declare existing lambda_s extern variable. + + * lib.c (obj_print, obj_pprint): print (lambda sym ...) + as (lambda (. sym) ...) and (lambda sym) as (lambda (. sym)). + + * txr.1: document it. + 2014-02-22 Kaz Kylheku Implemented macrolet. diff --git a/eval.h b/eval.h index 83c885e9..2c517ff7 100644 --- a/eval.h +++ b/eval.h @@ -24,7 +24,7 @@ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE. */ -extern val dwim_s, vector_lit_s, vector_list_s; +extern val dwim_s, lambda_s, vector_lit_s, vector_list_s; extern val hash_lit_s, hash_construct_s; extern val eval_error_s; extern val last_form_evaled; diff --git a/lib.c b/lib.c index 7037585f..0c257102 100644 --- a/lib.c +++ b/lib.c @@ -5213,8 +5213,22 @@ val obj_print(val obj, val out) put_char(chr('('), out); } + if (sym == lambda_s && cdr(obj) && symbolp(second(obj))) { + obj_print(sym, out); + if (second(obj)) { + put_string(lit(" (. "), out); + obj_print(second(obj), out); + put_char(chr(')'), out); + } else { + put_string(lit(" ()"), out); + } + iter = (cdr(obj)); + goto finish; + } + for (iter = obj; consp(iter); iter = cdr(iter)) { obj_print(car(iter), out); +finish: if (nilp(cdr(iter))) { put_char(closepar, out); } else if (consp(cdr(iter))) { @@ -5379,8 +5393,22 @@ val obj_pprint(val obj, val out) put_char(chr('('), out); } + if (sym == lambda_s && cdr(obj) && symbolp(second(obj))) { + obj_print(sym, out); + if (second(obj)) { + put_string(lit(" (. "), out); + obj_print(second(obj), out); + put_char(chr(')'), out); + } else { + put_string(lit(" ()"), out); + } + iter = (cdr(obj)); + goto finish; + } + for (iter = obj; consp(iter); iter = cdr(iter)) { obj_pprint(car(iter), out); +finish: if (nilp(cdr(iter))) { put_char(closepar, out); } else if (consp(cdr(iter))) { diff --git a/parser.y b/parser.y index a2553f88..819630b9 100644 --- a/parser.y +++ b/parser.y @@ -702,6 +702,7 @@ hash : HASH_H list { if (unquotes_occur($2)) list : '(' n_exprs ')' { $$ = rl($2, num($1)); } | '(' ')' { $$ = nil; } + | '(' '.' n_expr ')' { $$ = $3; } | '[' n_exprs ']' { $$ = rl(cons(dwim_s, $2), num($1)); } | '[' ']' { $$ = rl(cons(dwim_s, nil), num($1)); } | '@' n_expr { if (consp($2)) diff --git a/txr.1 b/txr.1 index 0299f698..8e663236 100644 --- a/txr.1 +++ b/txr.1 @@ -4845,6 +4845,33 @@ Much of the TXR Lisp syntax has been introduced in the previous sections of the manual, since directive forms are based on it. There is some additional syntax that is useful in TXR Lisp programming. +.SS Consing Dot + +Unlike other major Lisp dialects, TXR Lisp allows a consing dot with no forms +preceding it. This construct simply denotes the form which follows the dot. +That is to say, the parser implements the following transformation: + + (. expr) -> expr + +This is convenient in writing function argument lists that only take +variable arguments. Instead of the syntax: + + (defun fun args ...) + +the following syntax can be used: + + (defun fun (. args) ...) + +When a lambda form is printed, it is printed in the following style. + + (lambda nil ...) -> (lambda () ...) + (lambda sym ...) -> (lambda (. sym) ...) + (lambda (sym) ...) -> (lambda (sym) ...) + +In no other circumstances is nil printed as (), or a symbol as (. sym). + +symbol is followed by a symbol. + .SS Quoting/Unquoting .IP 'form -- cgit v1.2.3