2011-05-31 101 views
7

我正在写一个函数,它需要在ping基于web的API时捕获一个速率限制错误。Sys.sleep()之前没有执行的函数()

我使用tryCatch捕获错误,而这个函数里面我指定以下误差函数:

error=function(e) { 
       warning(paste(e,"\nWaiting an hour for rate limit to reset...")) 
       Sys.sleep(3600) # Wait an hour for rate-limit to reset 
       return(user.info(user, ego.count)) 
      } 

的功能似乎工作,但检查输出日志剧本时,我注意到,警告信息不会被写入,直到的睡眠时间已用完。

我可以在与R控制台重现此问题:前Drew sucks被打印到控制台

print("Drew sucks") 
Sys.sleep(10) 

十秒钟通过。在我的功能中,我想在暂停发生之前向用户提供一些关于这种长时间停顿的反馈。

是什么导致了这种行为?

回答

3

对于它的地狱,请尝试:

system(sprintf('sleep %d', seconds)) 

假设你已经有了路径通常的* NIX睡眠命令。

+1

有一件事 - 如果使用'warning',那么用户可以使用'suppressWarnings'来不显示消息。采用这种解决方案需要另一种方法。 – Marek 2011-06-01 08:11:13

2

可能与输出缓冲 - 见?flush.console

+0

另一方面,控制台I/O永远不会被缓冲。 r可能是一个例外,但这将是一个惊喜,不是吗?另一种方案的灵感,我想看看(doh)... – TheBlastOne 2011-05-31 21:45:41

+2

添加'flush.console()'并没有解决从上面的“德鲁吸”示例中的问题。 – DrewConway 2011-05-31 21:51:09

3

默认情况下,警告不立即打印,而不是他们的顶级函数返回后打印出来。如果要立即打印,可以设置警告为'1',如果您想要停止打印,则设置为更高。

+0

嗯,重新阅读你的文章后,我不确定我是否真的在回答正确的问题。我以为你是在说要让警告()立即打印出来,是吗? – geoffjentry 2011-05-31 21:45:32

+0

我这样做,但问题似乎只适用于'warning'调用,就像我的'print'示例一样。 – DrewConway 2011-05-31 21:50:10

+0

这就是让我觉得我可能不会在提问的问题。如果我启动R并运行您的打印示例,我会得到打印输出,然后是延迟。如果在Sys.sleep()之前为你做同样的事情确实没有执行print(),那么其他事情正在发生(例如Hadley的回答)。 我确实认为你会碰到问题w /警告()正在一个函数或者虽然。 – geoffjentry 2011-05-31 21:52:15

7

您需要将immediate.=TRUE设置为警告功能或设置options(warn=1);和可能需要在调用Sys.sleep()之前添加flush.console()(在某些操作系统上)。

foo <- function() { 
    warning("uh-oh...", immediate.=TRUE) 
    flush.console() 
    Sys.sleep(5) 
    "done" 
} 
foo() 
# Warning in foo() : uh-oh... 
# [1] "done" 

具体细节在?warning的“详细信息”部分详细说明。要解释,“如果选项(警告= 0),警告将在顶层功能完成后存储并打印;如果选项(警告= 1),则会在打印时发出警告。

+0

这可能是一个操作系统问题,但在OS X上,该函数在打印警告之前仍然执行'Sys.sleep'调用。 – DrewConway 2011-05-31 22:00:29

+0

它适用于Windows和Ubuntu(而且Ubuntu不需要'flush.console()')。 – 2011-05-31 22:02:51

+0

@DrewConway它适用于我通过终端运行的OSX。你在GUI中吗? (或者更具体地说 - 哪一个,如果是的话) – 2011-05-31 22:12:48