Re: [Rd] Bug: broken exception handling in S4 methods

From: John Chambers <jmc_at_r-project.org>
Date: Wed, 21 Jul 2010 16:45:14 -0700

The problem in this example is (plausibly) that the argument evaluation code in method selection itself uses an internal C-level version of try(), overriding the user's setting.

If this is the bug, I'll have to defer to more expert advice on whether, and if so how, the code can adjust for the current exception handling. (There don't seem to be many uses of this R_try() mechanism.)

On 7/21/10 2:36 AM, Sklyar, Oleg (London) wrote:
> Hi all:
>
> we have noticed for quite a while that certain errors cannot be handled
> by R try, tryCatch etc blocks, but it was fairly difficult to understand
> what were the conditions for this incorrect behaviour. Finally I stabbed
> across a very understandable case, which is outlined in the (runnable)
> example below.
>
> The main message is: wrapping an S4 method call in a try block will not
> help if an error occurs in evaluating an argument to such a call; this
> works just fine for function calls (as opposed to S4 methods)
>
> The particular example is a result of trying to write a unit test for a
> constructor of a class object which should fail under certain
> conditions. This failure obviously need to be caught for the unit test
> to proceed. However, it is a general problem with handling some
> exceptions in R.
>
> # Consider a simple class MyClassA, which is derived from numeric and
> for which
> # we define a constructor (in form of a method). On its own this class
> works nicely
> # and so does exception handling of it:
>
> setClass("MyClassA",
> contains = "numeric",
> validity = function(object)
> {
> stopifnot(object[1] == object[2])
> TRUE
> }
> )
>
>
> setGeneric("MyClassA", function(x) standardGeneric("MyClassA"))
>
> setMethod("MyClassA",
> signature(x = "numeric"),
> function(x)
> {
> new("MyClassA", x)
> }
> )
>
> ## OK
> er = try({ MyClassA(c(1,2)) })
>
> ## OK (error in constructor)
> er = try({ MyClassA(c(1,2)) })
>
> ## OK (error evaluating argument to a function)
> er = try({ sin(MyClassA(c(1,2))) })
>
>
> # Now consider we define MyClassB that has MyClassA in a slot
> # and we define a constructor that takes such objects:
>
>
> setClassUnion("MyClassAOrNULL", c("MyClassA", "NULL"))
>
> setClass("MyClassB",
> representation(
> ca = "MyClassAOrNULL"
> ),
> prototype(ca = NULL)
> )
>
> setGeneric("MyClassB", function(x) standardGeneric("MyClassB"))
>
> setMethod("MyClassB",
> signature(x = "MyClassA"),
> function(x)
> {
> new("MyClassB", ca = x)
> }
> )
>
> ## OK
> b = MyClassB(MyClassA(c(1,1)))
>
> ## FAILS (error evaluating argument to a method)
> er = try({ MyClassB(MyClassA(c(1,2))) })
>
> # As you see the last error cannot be handled
>
>
> # Moreover. If we define a function and a method as function(x) x then
> # the function can be handled by try, yet the method cannot:
>
> f = function(x) x
>
> setGeneric("g", function(x) standardGeneric("g"))
> setMethod("g", "MyClassA", function(x) x)
>
> ## OK (error evaluating argument to a function)
> er = try({ f(MyClassA(c(1,2))) })
>
> ## FAILS (error evaluating argument to a method)
> er = try({ g(MyClassA(c(1,2))) })
>
>
>
>> sessionInfo()
> R version 2.11.0 Patched (2010-05-05 r51914)
> x86_64-unknown-linux-gnu
>
> locale:
> [1] LC_CTYPE=en_GB LC_NUMERIC=C LC_TIME=en_GB
> LC_COLLATE=en_GB
> [5] LC_MONETARY=C LC_MESSAGES=en_GB LC_PAPER=en_GB
> LC_NAME=C
> [9] LC_ADDRESS=C LC_TELEPHONE=C LC_MEASUREMENT=en_GB
> LC_IDENTIFICATION=C
>
> attached base packages:
> [1] splines stats graphics utils datasets grDevices methods
> base
>
>
> Dr Oleg Sklyar
> Research Technologist
> AHL / Man Investments Ltd
> +44 (0)20 7144 3803
> osklyar_at_ahl.com
>
> **********************************************************************
> Please consider the environment before printing this email or its attachments.
> The contents of this email are for the named addressees ...{{dropped:19}}
>
> ______________________________________________
> R-devel_at_r-project.org mailing list
> https://stat.ethz.ch/mailman/listinfo/r-devel
>



R-devel_at_r-project.org mailing list
https://stat.ethz.ch/mailman/listinfo/r-devel Received on Wed 21 Jul 2010 - 23:49:04 GMT

Archive maintained by Robert King, hosted by the discipline of statistics at the University of Newcastle, Australia.
Archive generated by hypermail 2.2.0, at Wed 21 Jul 2010 - 23:50:17 GMT.

Mailing list information is available at https://stat.ethz.ch/mailman/listinfo/r-devel. Please read the posting guide before posting to the list.

list of date sections of archive