Common lisp's UNWIND-PROTECT operator: an idea worth stealing.  It is a way of 
associating some 'cleanup sentence' with a 'protected sentence', such that the 
former always runs prior to exiting the latter, regardless of its status.  If 
the protected sentence throws an error, it is propagated, unless the cleanup 
sentence itself throws an error.

It can be implemented in j as in the appendix, as 'up'.  Given [x] u up v y, 
[x] u y is the protected sentence and [x] v y is the cleanup sentence.  The 
mechanism is considerably less error-prone than manual cleanup schemes, as it 
is easy to forget the possibility that a sentence might error.  The lifetime 
restrictions are sufficient for many applications; sufficiently complicated use 
cases will still require manual cleanup.

This allows (relatively) safe usage of file numbers, given e.g.

with_file=: (up (1!:22@])) (@: : ([.].)) (1!:21@:fboxname)

[x] u with_file y treats y as a filename, opens it, and passes the resulting 
file number to u.  After u finishes, the file is closed.

Much more importantly, it allows for (relatively) safe usage of locks that 
makes deadlocks unlikely.  Using the new mutex interfaces (10-14 T.):

under_lock=: [. up (13&T.@) [ (11&T.@].)

[x] u under_lock n y is the same as [x] u y, except that it locks n first, and 
ensures it is unlocked after.  I propose under_lock for inclusion in the 
standard library posthaste, so no one gets too used to writing 11 T. and 13 T. 
by hand except at great need.  (I think up would also be interesting, but am 
less invested in it and more put it forward for discussion.)

(Side-note: how come CCA and CVC are legal, but not CVA?  I think CVA should be 
uCv V vA.  That seems fairly obvious and consistent, and it would simplify the 
above definition of under_lock.  AVC should be analogous.  I think this was 
proposed this a while ago but nothing came of it.)

 -E

Appendix:

up=: {{
 try.
  r=. u y
 catcht.
  v y
  throw.
 catch.
  a=. 13!:12''
  b=. 13!:11''
  v y
  a 13!:8 b
 end.
 v y
 r }} : {{
 try.
  r=. x u y
 catcht.
  x v y
  throw.
 catch.
  a=. 13!:12''
  b=. 13!:11''
  x v y
  a 13!:8 b
 end.
 x v y
 r }}

(Questions: is it possible to avoid duplication of the monadic and dyadic 
cases?  Is it possible to get nicer propagation of error messages?)

----------------------------------------------------------------------
For information about J forums see http://www.jsoftware.com/forums.htm

Reply via email to