Henrik Bengtsson
2015-Jan-26 18:53 UTC
[Rd] Inspect a "delayed" assigned whose value throws an error?
Hi, I got an interesting programming challenge: How do you inspect an object which is assigned via delayedAssign() and that throws an error as soon as it is "touched" (=the value is evaluated)? Is it possible? MINIMAL EXAMPLE: $ R --vanilla> delayedAssign("foo", stop("Hey!"))(If you find this minimal example silly/obvious, please skip down to the real example at the end)> fooError: Hey!> str(foo)Error in str(foo) : Hey! In addition: Warning message: In str(foo) : restarting interrupted promise evaluation> mode(foo)Error in mode(foo) : Hey! In addition: Warning message: In mode(foo) : restarting interrupted promise evaluation> .Internal(inspect(foo))Error: Hey! In addition: Warning message: restarting interrupted promise evaluation> traceback()1: stop("Hey!") Is there anyway I can inspect this object using the R API without evaluating the value in the delayed assignment? Is it possible to test if this is a delayed assigned or not? BACKGROUND: The background to this is where I have a function in the R.oo package that scans namespaces for functions with a certain class attribute. For this I use is.function() and inherits() to inspect each object. An aroma.affymetrix user reported on a problem that boiled down to the following: # source("http://bioconductor.org/biocLite.R"); biocLite("hgu133a.db")> library("hgu133a.db") > is.function(hgu133aPFAM)Error: hgu133aPFAM is defunct. Please use select() if you need access to PFAM or PROSITE accessions.> .Internal(inspect(hgu133aPFAM))> traceback()3: stop(paste(msg, collapse = ""), call. = FALSE, domain = NA) 2: .Defunct(msg = msg) 1: (function () { if (grepl("PFAM", x)) { bimapName <- paste0(prefix, "PFAM") } else { bimapName <- paste0(prefix, "PROSITE") } x <- dc[[bimapName]] msg = wmsg(paste0(bimapName, " is defunct. ", "Please use select() if you need access to PFAM or PROSITE accessions. \n")) if (interactive()) { .Defunct(msg = msg) } })() My immediate solution is to perform those tests using tryCatch(), but this is interesting, because this function is such that the error is only thrown in interactive() sessions, i.e. the following works: $ Rscript -e "hgu133a.db::hgu133aPFAM" [...] NULL This is probably also why none of my aroma.affymetrix system tests caught this. Without tracing the source code behind, which seems quite nested, the above is why I believe the assignment is "delayed"; traceback() shows a body source code, the object evaluates to different things depending on interactive(). /Henrik
Hadley Wickham
2015-Jan-26 20:24 UTC
[Rd] Inspect a "delayed" assigned whose value throws an error?
If it was any other environment than the global, you could use substitute: e <- new.env() delayedAssign("foo", stop("Hey!"), assign.env = e) substitute(foo, e) delayedAssign("foo", stop("Hey!")) substitute(foo) Hadley On Mon, Jan 26, 2015 at 12:53 PM, Henrik Bengtsson <hb at biostat.ucsf.edu> wrote:> Hi, I got an interesting programming challenge: > > How do you inspect an object which is assigned via delayedAssign() and > that throws an error as soon as it is "touched" (=the value is > evaluated)? Is it possible? > > > MINIMAL EXAMPLE: > > $ R --vanilla >> delayedAssign("foo", stop("Hey!")) > > (If you find this minimal example silly/obvious, please skip down to > the real example at the end) > >> foo > Error: Hey! > >> str(foo) > Error in str(foo) : Hey! > In addition: Warning message: > In str(foo) : restarting interrupted promise evaluation > >> mode(foo) > Error in mode(foo) : Hey! > In addition: Warning message: > In mode(foo) : restarting interrupted promise evaluation > >> .Internal(inspect(foo)) > Error: Hey! > In addition: Warning message: > restarting interrupted promise evaluation > >> traceback() > 1: stop("Hey!") > > Is there anyway I can inspect this object using the R API without > evaluating the value in the delayed assignment? Is it possible to > test if this is a delayed assigned or not? > > > BACKGROUND: > The background to this is where I have a function in the R.oo package > that scans namespaces for functions with a certain class attribute. > For this I use is.function() and inherits() to inspect each object. > An aroma.affymetrix user reported on a problem that boiled down to the > following: > > # source("http://bioconductor.org/biocLite.R"); biocLite("hgu133a.db") >> library("hgu133a.db") >> is.function(hgu133aPFAM) > Error: hgu133aPFAM is defunct. Please use select() if you need access to PFAM > or PROSITE accessions. >> .Internal(inspect(hgu133aPFAM)) > >> traceback() > 3: stop(paste(msg, collapse = ""), call. = FALSE, domain = NA) > 2: .Defunct(msg = msg) > 1: (function () > { > if (grepl("PFAM", x)) { > bimapName <- paste0(prefix, "PFAM") > } > else { > bimapName <- paste0(prefix, "PROSITE") > } > x <- dc[[bimapName]] > msg = wmsg(paste0(bimapName, " is defunct. ", "Please use select() if you > need access to PFAM or PROSITE accessions. \n")) > if (interactive()) { > .Defunct(msg = msg) > } > })() > > My immediate solution is to perform those tests using tryCatch(), but > this is interesting, because this function is such that the error is > only thrown in interactive() sessions, i.e. the following works: > > $ Rscript -e "hgu133a.db::hgu133aPFAM" > [...] > NULL > > This is probably also why none of my aroma.affymetrix system tests > caught this. Without tracing the source code behind, which seems > quite nested, the above is why I believe the assignment is "delayed"; > traceback() shows a body source code, the object evaluates to > different things depending on interactive(). > > /Henrik > > ______________________________________________ > R-devel at r-project.org mailing list > https://stat.ethz.ch/mailman/listinfo/r-devel-- http://had.co.nz/
Henrik Bengtsson
2015-Jan-26 20:41 UTC
[Rd] Inspect a "delayed" assigned whose value throws an error?
On Mon, Jan 26, 2015 at 12:24 PM, Hadley Wickham <h.wickham at gmail.com> wrote:> If it was any other environment than the global, you could use substitute: > > e <- new.env() > delayedAssign("foo", stop("Hey!"), assign.env = e) > substitute(foo, e) > > delayedAssign("foo", stop("Hey!")) > substitute(foo)Hmm... interesting and odd. Unfortunately, this doesn't seem to help for reaching into the namespace of hgu133a.db and inspecting 'hgu133aPFAM', e.g.> library("hgu133a.db")> substitute(hgu133aPFAM, env=ns)Error: hgu133aPFAM is defunct. Please use select() if you need access to PFAM or PROSITE accessions.> evalq(substitute(hgu133aPFAM), envir=ns)Error: hgu133aPFAM is defunct. Please use select() if you need access to PFAM or PROSITE accessions.> evalq(substitute(hgu133aPFAM, env=ns), envir=ns)Error: hgu133aPFAM is defunct. Please use select() if you need access to PFAM or PROSITE accessions. Thanks, Henrik> > Hadley > > On Mon, Jan 26, 2015 at 12:53 PM, Henrik Bengtsson <hb at biostat.ucsf.edu> wrote: >> Hi, I got an interesting programming challenge: >> >> How do you inspect an object which is assigned via delayedAssign() and >> that throws an error as soon as it is "touched" (=the value is >> evaluated)? Is it possible? >> >> >> MINIMAL EXAMPLE: >> >> $ R --vanilla >>> delayedAssign("foo", stop("Hey!")) >> >> (If you find this minimal example silly/obvious, please skip down to >> the real example at the end) >> >>> foo >> Error: Hey! >> >>> str(foo) >> Error in str(foo) : Hey! >> In addition: Warning message: >> In str(foo) : restarting interrupted promise evaluation >> >>> mode(foo) >> Error in mode(foo) : Hey! >> In addition: Warning message: >> In mode(foo) : restarting interrupted promise evaluation >> >>> .Internal(inspect(foo)) >> Error: Hey! >> In addition: Warning message: >> restarting interrupted promise evaluation >> >>> traceback() >> 1: stop("Hey!") >> >> Is there anyway I can inspect this object using the R API without >> evaluating the value in the delayed assignment? Is it possible to >> test if this is a delayed assigned or not? >> >> >> BACKGROUND: >> The background to this is where I have a function in the R.oo package >> that scans namespaces for functions with a certain class attribute. >> For this I use is.function() and inherits() to inspect each object. >> An aroma.affymetrix user reported on a problem that boiled down to the >> following: >> >> # source("http://bioconductor.org/biocLite.R"); biocLite("hgu133a.db") >>> library("hgu133a.db") >>> is.function(hgu133aPFAM) >> Error: hgu133aPFAM is defunct. Please use select() if you need access to PFAM >> or PROSITE accessions. >>> .Internal(inspect(hgu133aPFAM)) >> >>> traceback() >> 3: stop(paste(msg, collapse = ""), call. = FALSE, domain = NA) >> 2: .Defunct(msg = msg) >> 1: (function () >> { >> if (grepl("PFAM", x)) { >> bimapName <- paste0(prefix, "PFAM") >> } >> else { >> bimapName <- paste0(prefix, "PROSITE") >> } >> x <- dc[[bimapName]] >> msg = wmsg(paste0(bimapName, " is defunct. ", "Please use select() if you >> need access to PFAM or PROSITE accessions. \n")) >> if (interactive()) { >> .Defunct(msg = msg) >> } >> })() >> >> My immediate solution is to perform those tests using tryCatch(), but >> this is interesting, because this function is such that the error is >> only thrown in interactive() sessions, i.e. the following works: >> >> $ Rscript -e "hgu133a.db::hgu133aPFAM" >> [...] >> NULL >> >> This is probably also why none of my aroma.affymetrix system tests >> caught this. Without tracing the source code behind, which seems >> quite nested, the above is why I believe the assignment is "delayed"; >> traceback() shows a body source code, the object evaluates to >> different things depending on interactive(). >> >> /Henrik >> >> ______________________________________________ >> R-devel at r-project.org mailing list >> https://stat.ethz.ch/mailman/listinfo/r-devel > > > > -- > http://had.co.nz/
Possibly Parallel Threads
- Inspect a "delayed" assigned whose value throws an error?
- Inspect a "delayed" assigned whose value throws an error?
- Inspect a "delayed" assigned whose value throws an error?
- DO NOT REPLY [Bug 5963] New: rsync fails with errors that make no sense...
- combine 3 affybatches