summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--debug.c4
-rw-r--r--eval.c8
-rw-r--r--lib.c26
-rw-r--r--lib.h6
-rw-r--r--sysif.c2
-rw-r--r--txr.125
6 files changed, 48 insertions, 23 deletions
diff --git a/debug.c b/debug.c
index 328cee20..5b79c7ca 100644
--- a/debug.c
+++ b/debug.c
@@ -202,11 +202,11 @@ val debug(val ctx, val bindings, val data, val line, val pos, val base)
}
if (equal(command, lit("b"))) {
- breakpoints = remqual(l, breakpoints);
+ breakpoints = remqual(l, breakpoints, nil);
push(l, &breakpoints);
} else if (equal(command, lit("d"))) {
val breakpoints_old = breakpoints;
- breakpoints = remqual(l, breakpoints);
+ breakpoints = remqual(l, breakpoints, nil);
if (breakpoints == breakpoints_old)
format(std_debug, lit("no such breakpoint\n"));
} else {
diff --git a/eval.c b/eval.c
index a1809aca..754e27bf 100644
--- a/eval.c
+++ b/eval.c
@@ -4414,7 +4414,7 @@ static val weave_while(val env)
if (!tuples)
return nil;
- tuple = remq(uniq, car(tuples));
+ tuple = remq(uniq, car(tuples), nil);
if (!tuple)
return nil;
@@ -5021,9 +5021,9 @@ void eval_init(void)
reg_fun(intern(lit("rmember"), user_package), func_n4o(rmember, 2));
reg_fun(intern(lit("member-if"), user_package), func_n3o(member_if, 2));
reg_fun(intern(lit("rmember-if"), user_package), func_n3o(rmember_if, 2));
- reg_fun(intern(lit("remq"), user_package), func_n2(remq));
- reg_fun(intern(lit("remql"), user_package), func_n2(remql));
- reg_fun(intern(lit("remqual"), user_package), func_n2(remqual));
+ reg_fun(intern(lit("remq"), user_package), func_n3o(remq, 2));
+ reg_fun(intern(lit("remql"), user_package), func_n3o(remql, 2));
+ reg_fun(intern(lit("remqual"), user_package), func_n3o(remqual, 2));
reg_fun(intern(lit("remove-if"), user_package), func_n3o(remove_if, 2));
reg_fun(intern(lit("keepq"), user_package), func_n3o(keepq, 2));
reg_fun(intern(lit("keepql"), user_package), func_n3o(keepql, 2));
diff --git a/lib.c b/lib.c
index 0134d477..7abdb95b 100644
--- a/lib.c
+++ b/lib.c
@@ -1476,17 +1476,21 @@ val rmember_if(val pred, val list, val key)
return found;
}
-val remq(val obj, val list_orig)
+val remq(val obj, val list_orig, val keyfun)
{
list_collect_decl (out, ptail);
val list = tolist(list_orig);
val lastmatch = cons(nil, list);
+ keyfun = default_bool_arg(keyfun);
gc_hint(list);
for (; list; list = cdr(list)) {
- if (car(list) == obj) {
+ val elem = car(list);
+ val key = keyfun ? funcall1(keyfun, elem) : elem;
+
+ if (key == obj) {
ptail = list_collect_nconc(ptail, ldiff(cdr(lastmatch), list));
lastmatch = list;
}
@@ -1495,16 +1499,21 @@ val remq(val obj, val list_orig)
return make_like(out, list_orig);
}
-val remql(val obj, val list_orig)
+val remql(val obj, val list_orig, val keyfun)
{
list_collect_decl (out, ptail);
val list = tolist(list_orig);
val lastmatch = cons(nil, list);
+ keyfun = default_bool_arg(keyfun);
+
gc_hint(list);
for (; list; list = cdr(list)) {
- if (eql(car(list), obj)) {
+ val elem = car(list);
+ val key = keyfun ? funcall1(keyfun, elem) : elem;
+
+ if (eql(key, obj)) {
ptail = list_collect_nconc(ptail, ldiff(cdr(lastmatch), list));
lastmatch = list;
}
@@ -1513,16 +1522,21 @@ val remql(val obj, val list_orig)
return make_like(out, list_orig);
}
-val remqual(val obj, val list_orig)
+val remqual(val obj, val list_orig, val keyfun)
{
list_collect_decl (out, ptail);
val list = tolist(list_orig);
val lastmatch = cons(nil, list);
+ keyfun = default_bool_arg(keyfun);
+
gc_hint(list);
for (; list; list = cdr(list)) {
- if (equal(car(list), obj)) {
+ val elem = car(list);
+ val key = keyfun ? funcall1(keyfun, elem) : elem;
+
+ if (equal(key, obj)) {
ptail = list_collect_nconc(ptail, ldiff(cdr(lastmatch), list));
lastmatch = list;
}
diff --git a/lib.h b/lib.h
index f17def75..179c0c66 100644
--- a/lib.h
+++ b/lib.h
@@ -550,9 +550,9 @@ val member(val item, val list, val testfun, val keyfun);
val rmember(val item, val list, val testfun, val keyfun);
val member_if(val pred, val list, val key);
val rmember_if(val pred, val list, val key);
-val remq(val obj, val list);
-val remql(val obj, val list);
-val remqual(val obj, val list);
+val remq(val obj, val list, val keyfun);
+val remql(val obj, val list, val keyfun);
+val remqual(val obj, val list, val keyfun);
val remove_if(val pred, val list, val key);
val keepq(val obj, val list_orig, val key);
val keepql(val obj, val list_orig, val key);
diff --git a/sysif.c b/sysif.c
index 5c9f583b..c3d86fb5 100644
--- a/sysif.c
+++ b/sysif.c
@@ -149,7 +149,7 @@ val at_exit_call(val func)
val at_exit_do_not_call(val func)
{
val old = at_exit_list;
- at_exit_list = remq(func, old);
+ at_exit_list = remq(func, old, nil);
return tnil(old == at_exit_list);
}
diff --git a/txr.1 b/txr.1
index 72607129..e524dbce 100644
--- a/txr.1
+++ b/txr.1
@@ -22429,9 +22429,9 @@ The sequence or hash table is returned.
.coNP Functions @, remq @ remql and @ remqual
.synb
-.mets (remq < object << list )
-.mets (remql < object << list )
-.mets (remqual < object << list )
+.mets (remq < object << list <> [ key-function ])
+.mets (remql < object << list <> [ key-function ])
+.mets (remqual < object << list <> [ key-function ])
.syne
.desc
The
@@ -22441,7 +22441,7 @@ and
.code remqual
functions produce a new list based on
.metn list ,
-removing the items which are
+removing the elements whose associated keys are
.codn eq ,
.code eql
or
@@ -22457,11 +22457,22 @@ is
.meta list
itself.
+If
+.meta key-function
+is omitted, then the element keys compared to
+.meta object
+are the elements themselves.
+Otherwise,
+.meta key-function
+is applied to each element and the resulting value
+is that element's key which is compared to
+.metn object .
+
.coNP Functions @, remq* @ remql* and @ remqual*
.synb
-.mets (remq* < object << list )
-.mets (remql* < object << list )
-.mets (remqual* < object << list )
+.mets (remq* < object < list )
+.mets (remql* < object < list )
+.mets (remqual* < object < list )
.syne
.desc
The