summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorKaz Kylheku <kaz@kylheku.com>2015-12-23 06:53:22 -0800
committerKaz Kylheku <kaz@kylheku.com>2015-12-23 06:53:22 -0800
commit7aacecd153ecfdd7b5c480dc419d4823e896ef1c (patch)
treec269c4ba9d46628a2d92989ebbe8ad3cad08ec52
parentcb1b866fcd40a733d4c0e4a3cfe3249e2f1df1f8 (diff)
downloadtxr-7aacecd153ecfdd7b5c480dc419d4823e896ef1c.tar.gz
txr-7aacecd153ecfdd7b5c480dc419d4823e896ef1c.tar.bz2
txr-7aacecd153ecfdd7b5c480dc419d4823e896ef1c.zip
Base value in :counter
* match.c (do_output_line, do_output): Decode (var expr) syntax as argument of :counter and implement displacement. * txr.1: Documented.
-rw-r--r--match.c22
-rw-r--r--txr.117
2 files changed, 33 insertions, 6 deletions
diff --git a/match.c b/match.c
index cf648a9f..999d971b 100644
--- a/match.c
+++ b/match.c
@@ -1786,7 +1786,14 @@ static void do_output_line(val bindings, val specline, val filter, val out)
val empty_clauses = pop(&clauses);
val mod_clauses = pop(&clauses);
val modlast_clauses = pop(&clauses);
- val counter = getplist(args, counter_k);
+ val counter_spec = getplist(args, counter_k);
+ val consp_counter = consp(counter_spec);
+ val counter = if3(consp_counter, first(counter_spec), counter_spec);
+ val counter_base = if3(consp_counter,
+ eval_with_bindings(second(counter_spec),
+ elem,
+ bindings,
+ counter_spec), zero);
val vars = getplist(args, vars_k);
val bind_cp = extract_bindings(bindings, elem, vars);
val max_depth = reduce_left(func_n2(max2),
@@ -1814,7 +1821,7 @@ static void do_output_line(val bindings, val specline, val filter, val out)
val bind_d = mapcar(func_n1(bind_cdr), bind_cp);
if (counter) {
- rplacd(counter_var, num_fast(i));
+ rplacd(counter_var, plus(num_fast(i), counter_base));
rplacd(counter_bind, bind_a);
bind_a = counter_bind;
}
@@ -1923,7 +1930,14 @@ static void do_output(val bindings, val specs, val filter, val out)
val empty_clauses = pop(&clauses);
val mod_clauses = pop(&clauses);
val modlast_clauses = pop(&clauses);
- val counter = getplist(args, counter_k);
+ val counter_spec = getplist(args, counter_k);
+ val consp_counter = consp(counter_spec);
+ val counter = if3(consp_counter, first(counter_spec), counter_spec);
+ val counter_base = if3(consp_counter,
+ eval_with_bindings(second(counter_spec),
+ first_elem,
+ bindings,
+ counter_spec), zero);
val vars = getplist(args, vars_k);
val bind_cp = extract_bindings(bindings, first_elem, vars);
val max_depth = reduce_left(func_n2(max2),
@@ -1947,7 +1961,7 @@ static void do_output(val bindings, val specs, val filter, val out)
val bind_d = mapcar(func_n1(bind_cdr), bind_cp);
if (counter) {
- rplacd(counter_var, num_fast(i));
+ rplacd(counter_var, plus(num_fast(i), counter_base));
rplacd(counter_bind, bind_a);
bind_a = counter_bind;
}
diff --git a/txr.1 b/txr.1
index dfcbdf1f..27e72bcd 100644
--- a/txr.1
+++ b/txr.1
@@ -7488,7 +7488,9 @@ using the main clause.
Repeat supports arguments.
.cblk
-.mets @(repeat [:counter << symbol ] [:vars <> ( symbol *)])
+.mets @(repeat
+.mets \ \ \ [:counter >> { symbol | >> ( symbol << expr )}]
+.mets \ \ \ [:vars <> ( symbol *)])
.cble
The
@@ -7496,7 +7498,18 @@ The
argument designates a symbol which will behave as an integer
variable over the scope of the clauses inside the repeat. The variable provides
access to the repetition count, starting at zero, incrementing with each
-repetition.
+repetition. If the the argument is given as
+.cblk
+.meti >> ( symbol << expr )
+.cblk
+then
+.meta expr
+is a Lisp expression whose value is taken as a displacement value which
+is added to each iteration of the counter. For instance
+.code :counter (c 1)
+specifies a counter
+.code c
+which counts from 1.
The
.code :vars