2013-08-01 14 views
6

mam grubsza tę funkcję:Nie rozumiem błąd „nie znaleziono obiektu” wewnątrz funkcji

plot_pca_models <- function(models, id) { 
    library(lattice) 

    splom(models, groups=id) 
} 

i dzwonię to tak:

plot_pca_models(data.pca, log$id) 

wyniki wich w tym błędzie :

Error in eval(expr, envir, enclos) : object 'id' not found 

kiedy nazywają go bez funkcji owijania:

splom(data.pca, groups=log$id) 

podnosi ten błąd:

Error in log$id : object of type 'special' is not subsettable 

ale kiedy to zrobić:

id <- log$id 
splom(models, groups=id) 

zachowuje się zgodnie z oczekiwaniami.

Proszę, czy ktoś może wyjaśnić, dlaczego zachowuje się tak i jak to poprawić? Dzięki.

btw: Jestem świadomy podobnych pytań tutaj np:

ale żaden z nich nie pomógł mi.

edit: Zgodnie z wnioskiem, nie jest pełna funkcja "plot_pca_models":

plot_pca_models <- function(data, id, sel=c(1:4), comp=1) { 
    # 'data' ... princomp objects 
    # 'id' ... list of samples id (classes) 
    # 'sel' ... list of models to compare 
    # 'comp' ... which pca component to compare 

    library(lattice) 

    models <- c() 
    models.size <- 1:length(data) 
    for(model in models.size) { 
    models <- c(models, list(data[[model]]$scores[,comp])) 
    } 
    names(models) <- 1:length(data) 

    models <- do.call(cbind, models[sel]) 

    splom(models, groups=id) 
} 

Edit2: udało mi się sprawić, że problem jest powtarzalny.

require(lattice) 
my.data <- data.frame(pca1 = rnorm(100), pca2 = rnorm(100), pca3 = rnorm(100)) 
my.id <- data.frame(id = sample(letters[1:4], 100, replace = TRUE)) 

plot_pca_models2 <- function(x, ajdi) { 
    splom(x, group = ajdi) 
} 

plot_pca_models2(x = my.data, ajdi = my.id$id) 

które produkują taki sam błąd jak powyżej.

+1

'log' jest funkcją w bazie R. Dobrą praktyką jest nie nazwać obiektów po funkcjach ... może to spowodować zamieszanie. – Thomas

+0

Nie wywołuj swoich obiektów 'log'. 'log' jest funkcją z pakietu' base'. Zmień nazwę i powiedz nam, czy problem nadal występuje. – shadow

+0

Dzieje się tak dlatego, że kraty używają niestandardowej oceny. Właściwie nie mówisz tego, czego chcesz, ale spróbuj 'print (splom (models, groups = id))' – hadley

Odpowiedz

2

Problemem jest to, że splom ocenia jego groups argumentu w niestandardowym way.A szybkie poprawki jest przepisać swoją funkcję tak, że konstruuje połączenie z odpowiednią składnią:

f <- function(data, id) 
eval(substitute(splom(data, groups=.id), list(.id=id))) 

# test it 
ir <- iris[-5] 
sp <- iris[, 5] 
f(ir, sp) 
+1

Świetnie, dzięki! Chociaż wygląda trochę brzydko :) i wciąż nie rozumiem, dlaczego tak trzeba to zrobić. Ale hej, przynajmniej to działa:) ... – WestFlame

2

log jest funkcją w bazie R. Dobrą praktyką jest nie nazwać obiektów po funkcjach ... może powodować zamieszanie. Wpisz log$test do czystego sesji R, a zobaczysz, co się dzieje:

object of type 'special' is not subsettable

+0

OK, dzięki za poradę, zmieniłem nazwę na log i teraz zachowuje się nieco inaczej. Pierwszy błąd jest taki sam, drugi znika (ale wynik wygląda na to, że grupy parametrów nie są w ogóle używane ... kolory na wykresie wyników są takie same) – WestFlame

+0

'log <- data.frame (a = 1: 5); log $ a' – Roland

+0

@WestFlame Czy odwołujesz się do 'id' nigdzie indziej wewnątrz' plot_pca_models'? – Thomas

2

Oto modyfikacja odpowiedzi Hong Oi. Najpierw polecam dołączenie identyfikatora w głównej ramce danych, tj.

my.data <- data.frame(pca1 = rnorm(100), pca2 = rnorm(100), pca3 = rnorm(100), id = sample(letters[1:4], 100, replace = TRUE)) 

..a następnie

plot_pca_models2 <- function(x, ajdi) { 
    Call <- bquote(splom(x, group = x[[.(ajdi)]]))  
    eval(Call) 
    } 
plot_pca_models2(x = my.data, ajdi = "id") 

Przyczyną zamieszania jest następujący wiersz w siatkowej ::: splom.formula:

groups <- eval(substitute(groups), data, environment(formula)) 

... którego jedynym punktem jest to, aby móc określić grupy bez cudzysłowu , czyli

# instead of 
splom(DATA, groups="ID") 
# you can now be much shorter, thanks to eval and substitute: 
splom(DATA, groups=ID) 

Ale oczywiście, to sprawia, że ​​korzystanie splom (i inne funkcje np substytut które wykorzystują „ocena niestandardowe”) trudniejszy w obsłudze od wewnątrz innych funkcji, jest niezgodne z philosop hy, która jest "głównie" stosowana w pozostałej części R.