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 oskl...@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@r-project.org mailing list https://stat.ethz.ch/mailman/listinfo/r-devel