UseMethod("t")
te dice que t()
es un ( S3 función genérica ) que tiene métodos para diferentes clases de objetos.
El sistema de despacho del método S3
Para las clases S3, puede usar la methods
función para enumerar los métodos para una función o clase genérica en particular.
> methods(t)
[1] t.data.frame t.default t.ts*
Non-visible functions are asterisked
> methods(class="ts")
[1] aggregate.ts as.data.frame.ts cbind.ts* cycle.ts*
[5] diffinv.ts* diff.ts kernapply.ts* lines.ts
[9] monthplot.ts* na.omit.ts* Ops.ts* plot.ts
[13] print.ts time.ts* [<-.ts* [.ts*
[17] t.ts* window<-.ts* window.ts*
Non-visible functions are asterisked
"Las funciones no visibles están marcadas con un asterisco" significa que la función no se exporta desde el espacio de nombres de su paquete. Aún puede ver su código fuente a través de la :::
función (es decir stats:::t.ts
), o usando getAnywhere()
. getAnywhere()
es útil porque no tiene que saber de qué paquete proviene la función.
> getAnywhere(t.ts)
A single object matching ‘t.ts’ was found
It was found in the following places
registered S3 method for t from namespace stats
namespace:stats
with value
function (x)
{
cl <- oldClass(x)
other <- !(cl %in% c("ts", "mts"))
class(x) <- if (any(other))
cl[other]
attr(x, "tsp") <- NULL
t(x)
}
<bytecode: 0x294e410>
<environment: namespace:stats>
El sistema de despacho del método S4
El sistema S4 es un sistema de envío de método más nuevo y es una alternativa al sistema S3. Aquí hay un ejemplo de una función S4:
> library(Matrix)
Loading required package: lattice
> chol2inv
standardGeneric for "chol2inv" defined from package "base"
function (x, ...)
standardGeneric("chol2inv")
<bytecode: 0x000000000eafd790>
<environment: 0x000000000eb06f10>
Methods may be defined for arguments: x
Use showMethods("chol2inv") for currently available ones.
La salida ya ofrece mucha información. standardGeneric
es un indicador de una función S4. El método para ver los métodos S4 definidos se ofrece de manera útil:
> showMethods(chol2inv)
Function: chol2inv (package base)
x="ANY"
x="CHMfactor"
x="denseMatrix"
x="diagonalMatrix"
x="dtrMatrix"
x="sparseMatrix"
getMethod
se puede usar para ver el código fuente de uno de los métodos:
> getMethod("chol2inv", "diagonalMatrix")
Method Definition:
function (x, ...)
{
chk.s(...)
tcrossprod(solve(x))
}
<bytecode: 0x000000000ea2cc70>
<environment: namespace:Matrix>
Signatures:
x
target "diagonalMatrix"
defined "diagonalMatrix"
También hay métodos con firmas más complejas para cada método, por ejemplo
require(raster)
showMethods(extract)
Function: extract (package raster)
x="Raster", y="data.frame"
x="Raster", y="Extent"
x="Raster", y="matrix"
x="Raster", y="SpatialLines"
x="Raster", y="SpatialPoints"
x="Raster", y="SpatialPolygons"
x="Raster", y="vector"
Para ver el código fuente de uno de estos métodos, debe proporcionarse la firma completa, p. Ej.
getMethod("extract" , signature = c( x = "Raster" , y = "SpatialPolygons") )
No será suficiente proporcionar la firma parcial
getMethod("extract",signature="SpatialPolygons")
#Error in getMethod("extract", signature = "SpatialPolygons") :
# No method found for function "extract" and signature SpatialPolygons
Funciones que llaman funciones no exportadas
En el caso de ts.union
, .cbindts
y .makeNamesTs
son funciones no exportadas del stats
espacio de nombres. Puede ver el código fuente de funciones no exportadas utilizando el :::
operador o getAnywhere
.
> stats:::.makeNamesTs
function (...)
{
l <- as.list(substitute(list(...)))[-1L]
nm <- names(l)
fixup <- if (is.null(nm))
seq_along(l)
else nm == ""
dep <- sapply(l[fixup], function(x) deparse(x)[1L])
if (is.null(nm))
return(dep)
if (any(fixup))
nm[fixup] <- dep
nm
}
<bytecode: 0x38140d0>
<environment: namespace:stats>
Funciones que llaman código compilado
Tenga en cuenta que "compilado" no se refiere al código R compilado en bytes creado por el paquete del compilador . La <bytecode: 0x294e410>
línea en la salida anterior indica que la función está compilada en bytes, y aún puede ver la fuente desde la línea de comando R.
Funciones esa llamada .C
, .Call
, .Fortran
, .External
, .Internal
, o .Primitive
están llamando a los puntos de entrada en el código compilado, por lo que tendrá que buscar en las fuentes del código compilado, si se quiere entender completamente la función. Este espejo GitHub del código fuente R es un lugar decente para comenzar. La función pryr::show_c_source
puede ser una herramienta útil, ya que le llevará directamente a una página de GitHub para .Internal
y .Primitive
llamadas. Los paquetes pueden utilizar .C
, .Call
, .Fortran
, y .External
; pero no .Internal
o .Primitive
porque se usan para llamar a funciones integradas en el intérprete R.
Las llamadas a algunas de las funciones anteriores pueden usar un objeto en lugar de una cadena de caracteres para hacer referencia a la función compilada. En esos casos, el objeto es de la clase "NativeSymbolInfo"
, "RegisteredNativeSymbol"
o "NativeSymbol"
; e imprimir el objeto produce información útil. Por ejemplo, optim
llamadas .External2(C_optimhess, res$par, fn1, gr1, con)
(tenga en cuenta que C_optimhess
no "C_optimhess"
). optim
está en el paquete de estadísticas, por lo que puede escribir stats:::C_optimhess
para ver información sobre la función compilada que se llama.
Código compilado en un paquete
Si desea ver el código compilado en un paquete, deberá descargar / desempaquetar la fuente del paquete. Los binarios instalados no son suficientes. El código fuente de un paquete está disponible en el mismo repositorio CRAN (o compatible con CRAN) desde el que se instaló originalmente el paquete. La download.packages()
función puede obtener la fuente del paquete por usted.
download.packages(pkgs = "Matrix",
destdir = ".",
type = "source")
Esto descargará la versión fuente del paquete Matrix y guardará el .tar.gz
archivo correspondiente en el directorio actual. El código fuente para las funciones compiladas se puede encontrar en el src
directorio del archivo sin comprimir y sin tartar. El paso de descompresión y descompresión se puede realizar desde afuera R
o desde adentro R
usando la untar()
función. Es posible combinar el paso de descarga y expansión en una sola llamada (tenga en cuenta que solo un paquete a la vez se puede descargar y desempaquetar de esta manera):
untar(download.packages(pkgs = "Matrix",
destdir = ".",
type = "source")[,2])
Alternativamente, si el desarrollo del paquete está alojado públicamente (por ejemplo, a través de GitHub , R-Forge o RForge.net ), probablemente pueda buscar el código fuente en línea.
Código compilado en un paquete base
Ciertos paquetes se consideran paquetes "básicos". Estos paquetes se envían con R y su versión se bloquea en la versión de R. Los ejemplos incluyen base
, compiler
, stats
, y utils
. Como tales, no están disponibles como paquetes descargables por separado en CRAN como se describió anteriormente. Más bien, son parte del árbol de origen R en directorios de paquetes individuales en /src/library/
. Cómo acceder a la fuente R se describe en la siguiente sección.
Código compilado integrado en el intérprete R
Si desea ver el código incorporado en el intérprete de R, deberá descargar / desempaquetar las fuentes de R; o puede ver las fuentes en línea a través del repositorio R Subversion o el espejo github de Winston Chang .
El artículo de noticias R de Uwe Ligges (PDF) (p. 43) es una buena referencia general de cómo ver el código fuente .Internal
y las .Primitive
funciones. Los pasos básicos son buscar primero el nombre de la función src/main/names.c
y luego buscar el nombre de "entrada C" en los archivos de src/main/*
.