2016-04-25 7 views
5

Ho una funzione del kernel in questo modo:Come estrapolare oltre i punti x passati a `ksmooth`?

x <- 1:100 
y <- rnorm(100, mean=(x/2000)^2) 
plot(x,y) 
kernel <- ksmooth(x,y, kernel="normal", bandwidth=10) 
print(kernel$y) 

Se provo a prevedere in un punto al di fuori della gamma di valori x, che mi darà NaN, poiché tenta di estrapolare al di là dei dati:

x <- 1:100 
y <- rnorm(100, mean=(x/2000)^2) 
plot(x,y) 
kernel <- ksmooth(x,y, kernel="normal", bandwidth=10, x.points=c(130)) 
print(kernel$y) 

> print(kernel$y) 
[1] NA 

Anche quando cambio range.x che non si muove:

x <- 1:100 
y <- rnorm(100, mean=(x/2000)^2) 
plot(x,y) 
kernel <- ksmooth(x,y, kernel="normal", bandwidth=10, range.x=c(1,200) , x.points=c(130)) 
print(kernel$y) 

> print(kernel$y) 
[1] NA 

Come faccio ad avere il 012.315.941.041.443 La funzioneestrapola oltre i dati? So che questa è una cattiva idea in teoria, ma in pratica questo problema si presenta sempre.

+0

Suppongo che una domanda secondaria sia: * Cosa fa 'range.x'? * La documentazione sembra indicare che è" la gamma di punti da coprire nell'output. " Ma non sembra avere un effetto sull'output qui? – Hunle

+1

Hai preso in considerazione l'utilizzo di bkde2D {KernSmooth}. Di default questo estrapola 1,5 volte la larghezza di banda in ciascuna direzione. Estrapola ulteriormente a tuo rischio e pericolo, e sii sicuro di capire cosa stai facendo ed i suoi limiti. Se hai davvero bisogno di estrapolare, forse dovresti considerare di adattare i dati a un modello che ha qualche relazione con la realtà e costituisce una base più ragionevole per l'estrapolazione. – dww

+0

Farò una prova. Il problema è che è davvero difficile eseguire una sorta di convalida incrociata di k-fold quando non c'è estrapolazione, perché ogni volta che divido la kth fold in treno e test, alcuni degli esempi di test sono inevitabilmente al di fuori della gamma di gli esempi di formazione. Sono l'unico frustrato da questo? – Hunle

risposta

2

Per rispondere alla domanda a fianco, guardando il codice di ksmooth, range.x viene utilizzato solo quando x.points non viene fornito in modo che questo spieghi perché non lo si vede utilizzato. Diamo un'occhiata al codice ksmooth:

function (x, y, kernel = c("box", "normal"), bandwidth = 0.5, 
    range.x = range(x), n.points = max(100L, length(x)), x.points) 
{ 
    if (missing(y) || is.null(y)) 
     stop("numeric y must be supplied.\nFor density estimation use density()") 
    kernel <- match.arg(kernel) 
    krn <- switch(kernel, box = 1L, normal = 2L) 
    x.points <- if (missing(x.points)) 
     seq.int(range.x[1L], range.x[2L], length.out = n.points) 
    else { 
     n.points <- length(x.points) 
     sort(x.points) 
    } 
    ord <- order(x) 
    .Call(C_ksmooth, x[ord], y[ord], x.points, krn, bandwidth) 
} 

Da questo vediamo che abbiamo bisogno di non fornire x.points per assicurarsi che range.x viene utilizzato. Se corri:

x <- 1:100 
y <- rnorm(100, mean=(x/2000)^2) 
plot(x,y) 
kernel <- ksmooth(x,y, kernel="normal", bandwidth=10, range.x=c(1,200)) 
plot(kernel$x, kernel$y) 

Ora vedrai che il tuo kernel è valutato oltre 100 (anche se non fino a 200). Aumentare il parametro della larghezza di banda consente di allontanarsi ulteriormente da 100.

Problemi correlati