R-`try`结合捕获所有控制台输出?

时间:2018-11-16 15:27:13

标签: r error-handling

这是我正在使用的一段代码:

install.package('BiocManager');BiocManager::install('UniProt.ws')
requireNamespace('UniProt.ws')
uniprot_object <- UniProt.ws::UniProt.ws(
  UniProt.ws::availableUniprotSpecies(
    pattern = '^Homo sapiens$')$`taxon ID`)
query_results <- try(
    UniProt.ws::select(
      x = uniprot_object,
      keys = 'BAA08084.1',
      keytype = 'EMBL/GENBANK/DDBJ',
      columns = c('ENSEMBL','UNIPROTKB')))

此特定的键/键类型组合无效,并产生以下输出:

Getting mapping data for BAA08084.1 ... and ACC
error while trying to retrieve data in chunk 1:
  no lines available in input
continuing to try
Error in `colnames<-`(`*tmp*`, value = `*vtmp*`) : 
  attempt to set 'colnames' on an object with less than two dimensions

在报告的两个[eE]rror中,只有第二个是“正确的” R错误对象,并且使用了相应地捕获在变量try中的query_result。 / p>

但是,我非常想捕获其他error位(no lines available in input)来通知下游编程过程。

在使用通过开始分页(搜索)找到的大量capture.outputsinkpurrr::quietly等选项后,我仍然无法捕获该位。我该怎么办?

2 个答案:

答案 0 :(得分:2)

按照@Csd的建议,您可以使用tryCatch。您所关注的消息是通过R中的message()函数而不是stop()打印的,因此try()将忽略它。要捕获message()的输出,请使用如下代码:

query_results <- tryCatch(
   UniProt.ws::select(
     x = uniprot_object,
     keys = 'BAA08084.1',
     keytype = 'EMBL/GENBANK/DDBJ',
     columns = c('ENSEMBL','UNIPROTKB')), 
   message = function(e) conditionMessage(e))

这将在收到任何消息时中止评估,并在query_results中返回该消息。如果您要做的不仅仅是调试,您可能希望保存消息,但评估必须继续。在这种情况下,请改用withCallingHandlers。例如,

saveMessages <- c()
query_results <- withCallingHandlers(
   UniProt.ws::select(
     x = uniprot_object,
     keys = 'BAA08084.1',
     keytype = 'EMBL/GENBANK/DDBJ',
     columns = c('ENSEMBL','UNIPROTKB')), 
   message = function(e) 
               saveMessages <<- c(saveMessages, conditionMessage(e)))

运行此版本时,query_results不变(因为稍后的错误中止了执行),但是消息已保存:

saveMessages
[1] "Getting mapping data for BAA08084.1 ... and ACC\n"                                                    
[2] "error while trying to retrieve data in chunk 1:\n    no lines available in input\ncontinuing to try\n"

答案 1 :(得分:0)

基于@ user2554330的最佳答案,我构造了一个丑陋的东西,完全符合我的要求:

  1. 尝试执行该语句
  2. 不要致命地失败
  3. 不留下难看的消息
  4. 允许我访问errormessage s

这就是所有卑鄙的荣耀:

  saveMessages <- c()
  query_results <- suppressMessages(
    withCallingHandlers(
      try(
        UniProt.ws::select(
          x = uniprot_object,
          keys = 'BAA08084.1',
          keytype = 'EMBL/GENBANK/DDBJ',
          columns = c('ENSEMBL','UNIPROTKB')),
        silent = TRUE),
      message = function(e)
        saveMessages <<- c(saveMessages, conditionMessage(e))))
相关问题