trace
位於 base
包(package)。 說明
調用trace
允許您插入調試代碼(例如,調用browser
或者recover
)在任何函數中的選定位置。調用untrace
取消追蹤。可以以相同的方式跟蹤指定的方法,而無需跟蹤對通用函數的所有調用。跟蹤代碼(tracer
) 可以是任何R表達。可以通過調用全局暫時打開或關閉跟蹤tracingState
.
用法
trace(what, tracer, exit, at, print, signature,
where = topenv(parent.frame()), edit = FALSE)
untrace(what, signature = NULL, where = topenv(parent.frame()))
tracingState(on = NULL)
.doTrace(expr, msg)
returnValue(default = NULL)
參數
what |
要跟蹤或不跟蹤的函數的名稱,可能是 |
tracer |
function 或未計算的表達式。將在調用開始時或在參數 |
exit |
|
at |
可選的數字向量或列表。如果提供, |
print |
如果 |
signature |
如果提供此參數,它應該是函數 |
edit |
對於複雜的跟蹤,例如在函數內的循環內進行跟蹤,您將需要通過編輯函數體來插入所需的調用。如果是這樣,請將 |
where |
在哪裏尋找要跟蹤的函數;默認情況下,調用 此參數的一個重要用途是跟蹤 “hidden” 包中的函數或從另一個包調用的函數。命名空間機製導入要調用的函數(基礎包中的函數除外)。被調用的函數是不是從頂層看到的相同對象(通常,導入的包甚至可能不附加)。因此,您必須確保跟蹤正確的版本。做到這一點的方法是設置參數 |
on |
邏輯性;如果全局打開跟蹤,則對支持函數 |
expr, msg |
支持函數 |
default |
如果 |
細節
trace
函數通過構造函數(或方法,如果提供了 signature
)的修訂版本來運行,並將新對象分配回原始對象所在的位置。如果僅給出 what
參數,則每次調用該函數都會生成一行跟蹤打印(向後兼容 trace
的早期版本)。
trace
構造的對象來自擴展"function"
的類,其中包含原始的、未跟蹤的版本。調用 untrace
會重新分配此版本。
如果參數 tracer
或 exit
是函數名稱,則跟蹤表達式將是對該函數的調用,不帶參數。這是最簡單和最常見的情況,函數 browser
和 recover
是最有可能的候選者;前者在被跟蹤的函數框架中瀏覽,後者允許在任何當前活動的調用中瀏覽。對參數 tracer
和 exit
進行評估以查看它們是否是函數,但在跟蹤表達式中僅使用它們的名稱。當跟蹤函數執行時會再次進行查找,因此跟蹤時可能不會調用tracer
或exit
。
tracer
或 exit
參數也可以是未計算的表達式(例如通過調用 quote
或 substitute
返回)。該表達式本身插入到跟蹤函數中,因此它通常會涉及跟蹤函數中的參數或本地對象。如果您隻想在某些條件適用時進行交互,則這種形式的表達式非常有用(在這種情況下,您可能還想在對 trace
的調用中提供 print = FALSE
)。
當提供 at
參數時,它可以是引用函數體子步驟的整數向量(僅當函數體包含在 { ...}
中時才有效)。在這種情況下,tracer
不會在進入時調用,而是在評估 at
中列出的每個步驟之前調用。 (提示:您不想嘗試計算函數打印版本中的步驟;相反,請查看 as.list(body(f))
以獲取與函數 f
中的步驟關聯的數字。)
at
參數也可以是整數向量列表。在這種情況下,每個向量引用函數的另一個步驟中嵌套的一個步驟。例如,at = list(c(3,4))
將在函數第三步的第四步之前調用跟蹤器。請參閱下麵的示例。
使用 setBreakpoint
(來自包 utils
)可能是一種替代方法,調用 trace(...., at, ...)
。
exit
參數在 on.exit
處理期間調用。在on.exit
表達式中,可以調用實驗returnValue()
函數來獲取該函數將要返回的值。在其他情況下調用此函數將給出未定義的結果。
exit
參數的一個內在限製是,如果函數本身使用 on.exit
和 add=
FALSE
(默認),它將不起作用,因為現有調用將覆蓋 trace
提供的調用。
跟蹤不嵌套。對 trace
的任何調用都會替換該函數或方法之前跟蹤的版本(除了下麵討論的編輯版本),並且 untrace
始終恢複未跟蹤的版本。 (允許嵌套跟蹤很可能會造成混亂,並且可能會意外留下跟蹤版本。)
當重複使用 edit
參數且中間沒有在同一函數或方法上調用 untrace
時,將保留先前編輯的版本。如果您想丟棄所有先前的跟蹤然後進行編輯,請在下次調用 trace
之前調用 untrace
。編輯可與自動跟蹤相結合;隻需提供其他參數,例如 tracer
和 edit
參數。 edit = TRUE
參數使用默認編輯器(請參閱 edit
)。
從基礎包中跟蹤原始函數(內置函數和特殊函數)是可行的,但隻能通過特殊機製進行,並且信息量不大。跟蹤原語會導致原語被帶有參數的函數替換...(僅)。你可以得到一些信息,但不多。當在原語上使用 trace
時,會發出警告消息。
將函數的跟蹤版本保存回函數來源的位置的做法意味著,如果跟蹤函數保存在會話映像中,則跟蹤會從一個會話轉移到另一個會話。 (在下一個會話中,untrace
將刪除跟蹤。)另一方麵,包中而不是全局環境中的函數不會保存在映像中,因此跟蹤會隨著此類函數的會話而過期。
跟蹤 S4 方法本質上就像跟蹤函數一樣,不同之處在於跟蹤版本是通過調用 setMethod
而不是直接賦值來存儲的,調用 untrace
後的未跟蹤版本也是如此。
的版本trace
這裏說明的在很大程度上與S-Plus中的版本兼容,盡管兩者的工作機製完全不同。 S-Plustrace
使用會話框架,其結果是跟蹤永遠不會從一個會話轉移到另一個會話(R沒有會話框架)。另一個相關的區別與以下內容沒有直接關係trace
:S-Plus中的瀏覽器允許對正在瀏覽的框架進行更改,並且退出瀏覽器後更改將保留。這R瀏覽器允許更改,但當瀏覽器退出時它們就會消失。這可能是相關的,因為 S-Plus 版本允許您交互地試驗代碼更改,但是R版本沒有。 (未來的修訂版可能包括 ‘destructive’ 瀏覽器R.)
值
在簡單版本中(僅第一個參數), trace
返回不可見的 NULL
。否則,為跟蹤的函數名稱。相關的結果是發生的分配。
untrace
不可見地返回函數名稱。
tracingState
返回當前全局跟蹤狀態,並可能更改它。
在 on.exit
處理期間調用時,returnValue
返回退出函數即將返回的值。其他情況下的行為未定義。
注意
使用 trace()
在概念上是 debug
的泛化,但實現方式不同。即通過tracer
或exit
參數調用browser
。
包含除函數名稱之外的任何參數的函數跟蹤版本需要 methods
包(因為它使用特殊的對象類來存儲和恢複跟蹤函數的版本)。
如果當前未啟用方法調度,trace
將加載方法命名空間,但不會將方法包放在 search
列表中。
例子
require(stats)
## Very simple use
trace(sum)
hist(rnorm(100)) # shows about 3-4 calls to sum()
untrace(sum)
## Show how pt() is called from inside power.t.test():
if(FALSE)
trace(pt) ## would show ~20 calls, but we want to see more:
trace(pt, tracer = quote(cat(sprintf("tracing pt(*, ncp = %.15g)\n", ncp))),
print = FALSE) # <- not showing typical extra
power.t.test(20, 1, power=0.8, sd=NULL) ##--> showing the ncp root finding:
untrace(pt)
f <- function(x, y) {
y <- pmax(y, 0.001)
if (x > 0) x ^ y else stop("x must be positive")
}
## arrange to call the browser on entering and exiting
## function f
trace("f", quote(browser(skipCalls = 4)),
exit = quote(browser(skipCalls = 4)))
## instead, conditionally assign some data, and then browse
## on exit, but only then. Don't bother me otherwise
trace("f", quote(if(any(y < 0)) yOrig <- y),
exit = quote(if(exists("yOrig")) browser(skipCalls = 4)),
print = FALSE)
## Enter the browser just before stop() is called. First, find
## the step numbers
untrace(f) # (as it has changed f's body !)
as.list(body(f))
as.list(body(f)[[3]]) # -> stop(..) is [[4]]
## Now call the browser there
trace("f", quote(browser(skipCalls = 4)), at = list(c(3,4)))
## Not run:
f(-1,2) # --> enters browser just before stop(..)
## End(Not run)
## trace a utility function, with recover so we
## can browse in the calling functions as well.
trace("as.matrix", recover)
## turn off the tracing (that happened above)
untrace(c("f", "as.matrix"))
## Not run:
## Useful to find how system2() is called in a higher-up function:
trace(base::system2, quote(print(ls.str())))
## End(Not run)
##-------- Tracing hidden functions : need 'where = *'
##
## 'where' can be a function whose environment is meant:
trace(quote(ar.yw.default), where = ar)
a <- ar(rnorm(100)) # "Tracing ..."
untrace(quote(ar.yw.default), where = ar)
## trace() more than one function simultaneously:
## expression(E1, E2, ...) here is equivalent to
## c(quote(E1), quote(E2), quote(.*), ..)
trace(expression(ar.yw, ar.yw.default), where = ar)
a <- ar(rnorm(100)) # --> 2 x "Tracing ..."
# and turn it off:
untrace(expression(ar.yw, ar.yw.default), where = ar)
## Not run:
## trace calls to the function lm() that come from
## the nlme package.
trace("lm", where = asNamespace("nlme"))
lm (len ~ log(dose) * supp, ToothGrowth) -> fit1 # NOT traced
nlme::lmList(len ~ log(dose) | supp, ToothGrowth) -> fit2 # traced
untrace("lm", where = asNamespace("nlme"))
## End(Not run)
參考
Becker, R. A., Chambers, J. M. and Wilks, A. R. (1988) The New S Language. Wadsworth & Brooks/Cole.
也可以看看
browser
和 recover
,最有可能的跟蹤函數;另外,quote
和 substitute
用於構造通用表達式。
相關用法
- R tracemem 對象的跟蹤複製
- R traceback 獲取並打印調用堆棧
- R transform 轉換對象,例如 DataFrame
- R try 嘗試允許錯誤恢複的表達式
- R trimws 刪除前導/尾隨空格
- R taskCallback 添加或刪除頂級任務回調
- R toString 將 R 對象轉換為字符串或測試字符串
- R tilde 波形符運算符
- R textConnection 文本連接
- R t 矩陣轉置
- R table 交叉表和表格創建
- R tempfile 為臨時文件創建名稱
- R taskCallbackManager 創建R級任務回調管理器
- R typeof 對象的類型
- R taskCallbackNames 查詢當前內部頂級任務回調名稱
- R timezones 時區
- R tabulate 向量列表
- R tapply 對不規則數組應用函數
- R file.path 構造文件路徑
- R grep 模式匹配和替換
- R getwd 獲取或設置工作目錄
- R vector 向量 - 創建、強製等
- R lapply 對列表或向量應用函數
- R dump R 對象的文本表示
- R Sys.getenv 獲取環境變量
注:本文由純淨天空篩選整理自R-devel大神的英文原創作品 Interactive Tracing and Debugging of Calls to a Function or Method。非經特殊聲明,原始代碼版權歸原作者所有,本譯文未經允許或授權,請勿轉載或複製。