2015-12-10 3 views
1

У меня есть две функции, одна из которых вызывает другую в полурекурсивном режиме в зависимости от аргументов.trace, который включает переменную модификацию в testthat

f1 <- function(use_f2 = FALSE){ 
    if (use_f2) { 
    f2() 
    } 
} 

f2 <- function(){ 
    f1(use_f2 = FALSE) 
} 

Я хочу, чтобы отслеживать, сколько раз каждая функция вызывается в зависимости от аргументов, а затем, что в рамках модульного тестирования с использованием testthat.

я могу отслеживать, сколько вызовов производится с помощью настраиваемого среды и trace (см here за то, что я делал раньше), как показано в previous SO question

function_counts <- new.env() 
function_counts$f1 <- function_counts$f2 <- 0 

trace(f1, tracer = quote(function_counts$f1 <- function_counts$f1 + 1), print = FALSE) 
trace(f2, tracer = quote(function_counts$f2 <- function_counts$f2 + 1), print = FALSE) 

f1() 
function_counts$f1 
function_counts$f2 

Это работает хорошо, пока я не добавить осложнение окружающей среды testthat.

Если я ставлю

count_env <- new.env() 

count_env$f1 <- 0 

trace(f1, tracer = quote(count_env$f1 <<- count_env$f1 + 1), print = FALSE) 

либо снаружи, либо внутри test_that блока, и затем запустить devtools::test() или Ctrl-Shift-T в rstudio, который тестирует в особых условиях, я буду получать count_env not found. Я понимаю, что это все взаимодействие между средами trace и testthat, но я не могу его расшифровать.

Я также попытался сделать объект count_env объектом, не являющимся объектом самого пакета, но это тоже не сработало.

This Репо имеет минимальный пакет с этими двумя функциями и testthat тестирует каталог, чтобы играть с этим.

Любая помощь в том, куда идти отсюда, была бы замечательной.

+0

Этот вопрос по существу является дубликатом http://stackoverflow.com/questions/21687514/r-count-function-calls –

+0

Также, первый пример в ссылке, которую вы предоставляете, кажется, работает –

+0

@RomanTsegelskyi действительно? вызывая 'devtools :: test()' на пакете или Ctrl-shift-t в rstudio? потому что это всегда сбой для меня – rmflight

ответ

0

Оказывается, ответ заключается в использовании локальных переменных и функций местного, который определен в вызове trace.

.f1 <- .f2 <- 0 

trace(f1, tracer = function() {.f1 <<- .f1 + 1}, print = FALSE) 
trace(f2, tracer = function() {.f2 <<- .f2 + 1}, print = FALSE) 

test_that("f1 FALSE", { 
    f1() 
    expect_equal(1, .f1) 
    expect_equal(0, .f2) 
}) 

Благодаря Steph Локка для указывая на пример, в котором была использована анонимная функция, и для первоначального запроса тянуть.