Skip to content
Prev 23951 / 63421 Next

"try"ing to understand condition handling

Thanks; your response is very helpful.  This message has some remarks
on my questions relative to the developer docs, one additional
question, and some documentation comments.

I'm really glad to hear you plan to revise the exception/condition
docs. since I  found the existing ones a bit murky.

Below, [1] means
http://www.stat.uiowa.edu/~luke/R/exceptions/simpcond.html,
one of the documents Prof Ripley referred to.

That page also has a nice illustration of using the restart facility.
On Tue, Feb 20, 2007 at 01:40:11PM -0600, Luke Tierney wrote:
should have been "withCallingHandlers"
Handlers are specified as

name = fun

where name specifies an exception class and fun is a function of one
argument, the condition that is to be handled.  


...
The class relations are explicit in [1].
Here's the one point of clarification: does the preceding paragraph
about "all handlers are executed" apply only to withCallingHandlers,
or does it include tryCatch as well?  Rereading ?tryCatch, it still
looks as if the first match only will fire.
....
Great.  FWIW, here are some suggestions about the documentation:

I would find a presentation that provided an overall orientation and
then worked down easiest to follow.  So, goiing from the top down: 
1. there are 3 forms of exception handling: try/catch, calling
handlers and restarts.
2. the characteristic behavior of each is ... (i.e., what's the flow
of control).  Maybe give a snippet of typical uses of each.
3. the details (exact calling environment of the handler(s), matching
rules, syntax...)
4. try() is basically a convenient form of tryCatch.
5. Other relations between these 3 forms: what happens if they are
nested; how restarts alter the "standard" control flow of the other
forms.  I also found the info that the restart mechanism is the most
general and complicated useful for orientation (that might go under
point 1).

It might be appropriate to document each form on a separate manual
page; I'm not sure if they are too linked (particularly by the use of
conditions and the control flow of restart) to make that a good idea.

I notice that some of the outline above is not the standard R manual
format; maybe the big picture should go in the language manual or on a
concept page (?Exceptions maybe).

Be explicit about the relations between conditions (class inheritance
relations).

Be explicit about how handlers are chosen and which forms they take.

It might be worth mentioning stuff that is a little surprising.  The
fact that the value of  the finally is not the value of the tryCatch
was a little surprising, since usually the value of a series of
statements or expression is that of the last one.  The fact that
signalCondition can participate in two different flows of control
(discussion snipped above) was also surprising to me.  In both cases
the current ?tryCatch is pretty explicit already, so that's not the
issue.

I found the current language (for ?tryCatch) about the calling context
of different handlers a bit obscure.  For example, discussing tryCatch:
   " If a handler
     is found then control is transferred to the 'tryCatch' call that
     established the handler, the handler found and all more recent
     handlers are disestablished, the handler is called with the
     condition as its argument, and the result returned by the handler
     is returned as the value of the 'tryCatch' call."
It seems to me that control is transferred to within the tryCatch
call, rather than to the call itself.  I'd expect transferring control
to the call to re-execute the whole thing, ad infinitum.  I found the
seemingly less formal description in [1] easier to grasp:
" When an exception is signaled, the most recently established handler
that matches the exception (for which the exception inherits from the
specified class) is chosen, control transfers back to the try.catch
expression, the handler function is called, and the value returned by
the handler function is returned by the try.catch call. "

?tryCatch refers to "up" and "down" the stack in a few places.
Although there is really only one plausible reading, referring to
handlers established before or after the focal handler might be
clearer (at least in my head, I have an image of call stacks sometimes
going down in physical memory as they grow).

Ross