ben tam olarak nedenini açıklamak eğer emin değilim, ama sorunu izole ettik ve tamir edebiliriz. Temel sorun özyinelemedir: - özyinelemeli çağrı substitute(.FUN)
aradığında, .FUN
değerinin ne olduğunu bulmak için bir çağrı yığınının seviyesine çıkacaktır - bir sözün değerlendirmesini yeniden başlatmak zorundadır (gecikmiş yürütme işlev argümanları) bir seviye yukarı.
retry <- function(.FUN, max.attempts = 3, sleep.seconds = 0.5) {
expr <- substitute(.FUN)
retry_expr(expr, max.attempts, sleep.seconds)
}
retry_expr <- function(expr, max.attempts = 3, sleep.seconds = 0.5) {
x <- try(eval(expr))
if(inherits(x, "try-error") && max.attempts > 0) {
Sys.sleep(sleep.seconds)
return(retry_expr(expr, max.attempts - 1))
}
x
}
f <- function() {
x <- runif(1)
if (x < 0.5) stop("Error!") else x
}
retry(f())
ederim yerine kullanılmasını en aza tavsiye sen esnek kullanabilirsiniz işlevler oluşturmak için:
bir düzeltme kez ikame tıpkı etmektir. Tecrübemde, genellikle ikame işlemini yapan bir fonksiyona sahip olmanın en iyisi, ve tüm işi yapan başka bir şey. Başka bir işlevi çağrıldığında bu işlevi kullanmak mümkün kılar:
g1 <- function(fun) {
message("Function starts")
x <- retry(fun)
message("Function ends")
x
}
g1(f())
# Function starts
# Error in eval(expr, envir, enclos) : object 'fun' not found
# Error in eval(expr, envir, enclos) : object 'fun' not found
# Error in eval(expr, envir, enclos) : object 'fun' not found
# Error in eval(expr, envir, enclos) : object 'fun' not found
# Function ends
g2 <- function(fun) {
message("Function starts")
expr <- substitute(fun)
x <- retry_expr(expr)
message("Function ends")
x
}
g2(f())
# Function starts
# Error in f() : Error!
# Function ends
# [1] 0.8079241
.FUN'nuzun yinelemeli uygulamasının sürümünüzde çalışmayacağını düşünürdüm, çünkü .FUN bu noktada zaten değerlendirilmiş olurdu? Bunu test edeceğim ... – Shane
Sanırım haklısın, ama bu arada bunu anladım. Sanırım f benim daha iyi bir örnek çünkü bazen hatalar ve bazen de değil. Beklediğiniz şeyi kontrol etmek için birkaç kez çalıştırın. Denemelerin bittiğinde geri dönmek istediğinden emin değilim ama hala bir hatam var. – hadley
Oh, Görüyorsunuz ki, postanızın alt kısmına bir eşdeğiniz vardı:/ – hadley