From d212fc6284a6b7858da4570ef4d22cb88eec747a Mon Sep 17 00:00:00 2001 From: Kaz Kylheku Date: Fri, 16 Jun 2017 06:40:49 -0700 Subject: Support ref, refset on structs via lambda, lambda-set. * lib.c (ref, refset): Check for lambda and lambda-set, respectively, and use it. * txr.1: Documented. * tests/012/aseq.tl (add lambda): Fix previously unused broken method which now causes test to go into infinite recursion. --- lib.c | 11 +++++++++++ tests/012/aseq.tl | 2 +- txr.1 | 18 ++++++++++++++++++ 3 files changed, 30 insertions(+), 1 deletion(-) diff --git a/lib.c b/lib.c index 800142a2..bb5e7e51 100644 --- a/lib.c +++ b/lib.c @@ -9246,6 +9246,11 @@ val ref(val seq, val ind) return gethash(seq, ind); if (seq->co.cls == carray_s) return carray_ref(seq, ind); + if (structp(seq)) { + val lambda_meth = maybe_slot(seq, lambda_s); + if (lambda_meth) + return funcall2(lambda_meth, seq, ind); + } /* fallthrough */ case CONS: case LCONS: @@ -9283,6 +9288,12 @@ val refset(val seq, val ind, val newval) return sethash(seq, ind, newval); if (seq->co.cls == carray_s) return carray_refset(seq, ind, newval); + if (structp(seq)) { + val lambda_set_meth = maybe_slot(seq, lambda_set_s); + if (lambda_set_meth) + return funcall3(lambda_set_meth, seq, ind, newval); + } + /* fallthrough */ default: type_mismatch(lit("ref: ~s is not a sequence"), seq, nao); } diff --git a/tests/012/aseq.tl b/tests/012/aseq.tl index 7901c4ab..fc6cf76b 100644 --- a/tests/012/aseq.tl +++ b/tests/012/aseq.tl @@ -5,7 +5,7 @@ (:method cdr (me) (if (cdr me.list) (new (add me.n (cdr me.list))))) (:method car (me) (+ me.n (car me.list))) (:method nullify (me) (if me.list me)) - (:method lambda (me i) (ref me i))) + (:method lambda (me i) (+ me.n (ref me.list i)))) (defvarl o (new (add 3 (range 10 100 10)))) diff --git a/txr.1 b/txr.1 index 40eea806..3251c3f6 100644 --- a/txr.1 +++ b/txr.1 @@ -25596,6 +25596,24 @@ has retrieval and storage; in that case .meta index isn't restricted to an integer value. +If +.meta seq +is a structure, it supports +.code ref +if it has a +.code lambda +method. The +.meta index +argument is passed to that method, and the resulting value is +returned. Similarly, a structure supports +.code refset +if it has a +.code lambda-set +method, which is called with +.meta index +and +.metn new-value . + The .code ref function retrieves an element of -- cgit v1.2.3