Frage

Ich brauche ein paar simulierten Daten zu glätten, aber gelegentlich zu Problemen führen, wenn die simulierten Koordinaten geglättet werden meist der gleiche Wert. Hier ist ein kleines reproduzierbares Beispiel für den einfachstenen Fall.

> x <- 0:50
> y <- rep(0,51)
> loess.smooth(x,y)
Error in simpleLoess(y, x, w, span, degree, FALSE, FALSE, normalize = FALSE,  : 
   NA/NaN/Inf in foreign function call (arg 1)

loess(y~x), lowess(x,y) und ihre analogen in MATLAB erzeugen die erwarteten Ergebnisse ohne Fehler in diesem Beispiel. Ich verwende loess.smooth hier, weil ich die Schätzungen bei einer bestimmten Anzahl von Punkten bewertet müssen. Gemäß der Dokumentation, glaube ich loess.smooth und loess die gleichen Schätzfunktionen verwenden, aber die erstere ist eine „Hilfsfunktion“ der Bewertungspunkte zu behandeln. Der Fehler scheint aus einer C-Funktion zu kommen:

> traceback()
3: .C(R_loess_raw, as.double(pseudovalues), as.double(x), as.double(weights), 
   as.double(weights), as.integer(D), as.integer(N), as.double(span), 
   as.integer(degree), as.integer(nonparametric), as.integer(order.drop.sqr), 
   as.integer(sum.drop.sqr), as.double(span * cell), as.character(surf.stat), 
   temp = double(N), parameter = integer(7), a = integer(max.kd), 
   xi = double(max.kd), vert = double(2 * D), vval = double((D + 
       1) * max.kd), diagonal = double(N), trL = double(1), 
   delta1 = double(1), delta2 = double(1), as.integer(0L))
2: simpleLoess(y, x, w, span, degree, FALSE, FALSE, normalize = FALSE, 
   "none", "interpolate", control$cell, iterations, control$trace.hat)
1: loess.smooth(x, y)

loess nennt auch simpleLoess, aber mit dem, was erscheint unterschiedliche Argumente zu sein. Natürlich müssen, wenn Sie genug der y-Werte werden von Null verschiedenen, loess.smooth läuft ohne Fehler variieren, aber ich das Programm auch den extremsten Fall zulaufen.

Ich hoffe, jemand kann mir helfen, mit einem und / oder alle der folgenden:

  1. Verstehen, warum nur loess.smooth, und nicht die anderen Funktionen, um diesen Fehler erzeugt und eine Lösung für dieses Problem finden.
  2. Finden Sie eine Behelfslösung loess verwenden, aber immer noch die Schätzung bei einer bestimmten Anzahl von Punkten bewerten, die von dem Vektor x unterscheiden können. Zum Beispiel könnte ich will nur x <- seq(0,50,10) in der Glättung verwenden, aber die Schätzung bei x <- 0:50 bewerten. Soweit ich weiß, wird mit predict mit einem neuen Datenrahmen nicht richtig mit dieser Situation umgehen, aber bitte lassen Sie mich wissen, ob ich da etwas fehle.
  3. Behandeln Sie die Fehler in einer Weise, dass das Programm nicht stoppen auf den nächsten simulierten Datensatz zu bewegen.

Vielen Dank im Voraus für jede Hilfe zu diesem Problem.

War es hilfreich?

Lösung

Für Teil 1: Dies dauerte etwas aufzuspüren, aber wenn Sie tun:

loess.smooth(x, y, family = "guassian")

wird das Modell passen. Dies ergibt sich aufgrund der verschiedenen Standardeinstellungen der loess.smooth und loess; Ersteres hat family = c("symmetric", "gaussian") während letztere hat es umgekehrt. Wenn Sie den Code für loess und loess.smooth forsten, werden Sie sehen, dass, wenn family = "gaussian" iterations zu 1 gesetzt. Ansonsten nimmt er den Wert loess.control()$iterations. Wenn Sie Iterationen in simpleLoess tun, gibt den folgenden Funktionsaufruf einen Vektor von NaN:

pseudovalues <- .Fortran(R_lowesp, as.integer(N), as.double(y), 
            as.double(z$fitted.values), as.double(weights), as.double(robust), 
            integer(N), pseudovalues = double(N))$pseudovalues

, die den nächsten Funktionsaufruf verursacht den Fehler werfen Sie sahen:

zz <- .C(R_loess_raw, as.double(pseudovalues), as.double(x), 
            as.double(weights), as.double(weights), as.integer(D), 
            as.integer(N), as.double(span), as.integer(degree), 
            as.integer(nonparametric), as.integer(order.drop.sqr), 
            as.integer(sum.drop.sqr), as.double(span * cell), 
            as.character(surf.stat), temp = double(N), parameter = integer(7), 
            a = integer(max.kd), xi = double(max.kd), vert = double(2 * 
                D), vval = double((D + 1) * max.kd), diagonal = double(N), 
            trL = double(1), delta1 = double(1), delta2 = double(1), 
            as.integer(0L))

bezieht sich alle auf robuste Montage in Löss (das Verfahren). Wenn Sie nicht möchten / müssen eine robuste Passform, Verwendung family = "gaussian" in Ihrem loess.smooth Anruf.

Auch beachten Sie, dass die Standardeinstellungen für loess.smooth unterscheiden sich von denen loess, z.B. für 'span' und 'degree'. So sorgfältig prüfen, was Modelle, die Sie passen wollen und stellen Sie die Standardeinstellungen des entsprechenden Funktion.

Für Teil 2:

DF <- data.frame(x = 0:50, y = rep(0,51))
mod <- loess(y ~ x, data = DF)
pred <- predict(mod, newdata = data.frame(x = c(-1, 10, 15, 55)))
mod2 <- loess(y ~ x, data = DF, control = loess.control(surface = "direct"))
pred2 <- predict(mod2, newdata = data.frame(x = c(-1, 10, 15, 55)))

Was gibt:

> pred
 1  2  3  4 
NA  0  0 NA 
> pred2
1 2 3 4 
0 0 0 0

Der Standard wird nicht extrapolieren, wenn das ist, was Sie meinen. Ich sehe nicht, was das Problem mit sich hier mit predict überhaupt ist, in der Tat.

Für Teil 3: Schauen Sie sich ?try und ?tryCatch, die Sie rund um die Löss Anpassungsfunktion (loess.smooth sagen wir) wickeln können, die Berechnungen ermöglicht es weiterhin, wenn ein Fehler in loess.smooth angetroffen wird.

Sie müssen die Ausgabe von try oder tryCatch zu handhaben, indem so etwas wie (wenn Sie dies in einer Schleife tun:

mod <- try(loess.smooth(x, y))
if(inherits(mod, "try-error"))
    next
## if here, model work, do something with `mod`

Ich würde wahrscheinlich try oder tryCatch mit passend über loess und mit predict für ein solches Problem kombinieren.

Andere Tipps

Dies ist das erste Mal, dass ich diese Funktionen anzutreffen, damit ich Ihnen, dass viel nicht helfen können, aber kann dies nicht etwas, mit mit einer Varianz von 0 in den y-Werten zu tun? Nun versuchen Sie eine glatte Linie von Daten zu schätzen, dass bereits so glatt wie es geht, und dies funktioniert:

x <- 0:50
y <- c(rep(0,25),rep(1,26))
loess.smooth(x,y)
Lizenziert unter: CC-BY-SA mit Zuschreibung
Nicht verbunden mit StackOverflow
scroll top