Noah Lavine <noah.b.lav...@gmail.com> writes: > On Thu, Mar 1, 2012 at 7:00 PM, David Kastrup <d...@gnu.org> wrote: >> >> Hi, >> >> I am just meddling around with coding and have come up with the >> following: >> >> (define-public (find-child music predicate) >> "Find the first node in @var{music} that satisfies @var{predicate}." >> (catch 'music-found >> (lambda () >> (fold-some-music predicate >> (lambda (music . _) (throw 'music-found music)) >> #f music)) >> (lambda (key music) music))) >> >> Now the problem with that is that it is unhygienic. If fold-some-music >> were to use music-found signals, or if the predicate did, things would >> be awkward. One would need to work with a uniquely generated symbol. >> It turns out that the above can be expressed much clearer and cleaner as >> >> (define-public (find-child music predicate) >> "Find the first node in @var{music} that satisfies @var{predicate}." >> (call-with-current-continuation >> (lambda (music-found) >> (fold-some-music predicate >> (lambda (music . _) (music-found music)) >> #f music)))) >> >> at least if I did not make some thinko here. It is basically the same >> code and stack-upwards-only, but hygienic. Nothing can call the >> continuation but what is inside. Well, of course fold-some-music could >> save the closure calling music-found for later. But it doesn't. >> >> Is there a way to get a call-with-current-continuation that does not >> create a stack copy? It is fine if it fails with an exception if one >> still tries calling the continuation after it has already returned. > > If I understand correctly, you only need to call the continuation > once. Is that right? > > In that case, I think you could use either catch and throw or prompts.
Neither of which are hygienic and also less straightforward. It is not like I did not start my posting by giving the catch/throw-based example and saying what I disliked about it. -- David Kastrup