wake-up-neo.com

Wie schreibt man eine Formel mit vielen Variablen aus einem Datenrahmen?

Angenommen, ich habe eine Antwortvariable und Daten, die drei Kovariaten enthalten (als Spielzeugbeispiel):

y = c(1,4,6)
d = data.frame(x1 = c(4,-1,3), x2 = c(3,9,8), x3 = c(4,-4,-2))

Ich möchte eine lineare Regression an die Daten anpassen:

fit = lm(y ~ d$x1 + d$x2 + d$y2)

Gibt es eine Möglichkeit, die Formel zu schreiben, damit ich nicht jede einzelne Kovariate ausschreiben muss? Zum Beispiel so etwas

fit = lm(y ~ d)

(Ich möchte, dass jede Variable im Datenrahmen eine Kovariate ist.) Ich frage, weil ich tatsächlich 50 Variablen in meinem Datenrahmen habe, und ich möchte vermeiden, dass x1 + x2 + x3 + etc geschrieben wird.

106
grautur

Es gibt einen speziellen Bezeichner, den man in einer Formel verwenden kann, um alle Variablen zu bezeichnen. Dies ist der Bezeichner ..

y <- c(1,4,6)
d <- data.frame(y = y, x1 = c(4,-1,3), x2 = c(3,9,8), x3 = c(4,-4,-2))
mod <- lm(y ~ ., data = d)

Sie können auch die folgenden Aktionen ausführen, um alle Variablenleiste eins zu verwenden:

mod <- lm(y ~ . - x3, data = d)

Technisch bedeutet .alle Variablen nicht , die bereits in der Formel erwähnt wurden. Zum Beispiel

lm(y ~ x1 * x2 + ., data = d)

dabei würde . nur auf x3 verweisen, da x1 und x2 bereits in der Formel enthalten sind.

167
Gavin Simpson

Ein etwas anderer Ansatz besteht darin, Ihre Formel aus einer Zeichenfolge zu erstellen. In der formula-Hilfeseite finden Sie das folgende Beispiel:

## Create a formula for a model with a large number of variables:
xnam <- paste("x", 1:25, sep="")
fmla <- as.formula(paste("y ~ ", paste(xnam, collapse= "+")))

Wenn Sie dann die generierte Formel betrachten, erhalten Sie:

R> fmla
y ~ x1 + x2 + x3 + x4 + x5 + x6 + x7 + x8 + x9 + x10 + x11 + 
    x12 + x13 + x14 + x15 + x16 + x17 + x18 + x19 + x20 + x21 + 
    x22 + x23 + x24 + x25
57
juba

Ja, natürlich fügen Sie einfach die Antwort y als erste Spalte im Datenrahmen hinzu und rufen Sie lm() auf:

d2<-data.frame(y,d)
> d2
  y x1 x2 x3
1 1  4  3  4
2 4 -1  9 -4
3 6  3  8 -2
> lm(d2)

Call:
lm(formula = d2)

Coefficients:
(Intercept)           x1           x2           x3  
    -5.6316       0.7895       1.1579           NA  

Meine Informationen über R weisen auch darauf hin, dass die Zuweisung mit <- über = empfohlen wird.

7
Bernd Elkemann

Eine Erweiterung der Methode von juba besteht darin, reformulate zu verwenden, eine Funktion, die explizit für eine solche Aufgabe entwickelt wurde.

## Create a formula for a model with a large number of variables:
xnam <- paste("x", 1:25, sep="")

reformulate(xnam, "y")
y ~ x1 + x2 + x3 + x4 + x5 + x6 + x7 + x8 + x9 + x10 + x11 + 
    x12 + x13 + x14 + x15 + x16 + x17 + x18 + x19 + x20 + x21 + 
    x22 + x23 + x24 + x25

Für das Beispiel im OP wäre die einfachste Lösung hier

# add y variable to data.frame d
d <- cbind(y, d)
reformulate(names(d)[-1], names(d[1]))
y ~ x1 + x2 + x3

oder 

mod <- lm(reformulate(names(d)[-1], names(d[1])), data=d)

Beachten Sie, dass das Hinzufügen der abhängigen Variablen zum data.frame in d <- cbind(y, d) nicht nur deshalb bevorzugt wird, weil reformulate verwendet werden kann, sondern auch, weil das lm-Objekt in Funktionen wie predict zukünftig verwendet werden kann.

3
lmo

Ich baue diese Lösung, reformulate kümmert sich nicht darum, ob Variablennamen Leerzeichen haben.

add_backticks = function(x) {
    paste0("`", x, "`")
}

x_lm_formula = function(x) {
    paste(add_backticks(x), collapse = " + ")
}

build_lm_formula = function(x, y){
    if (length(y)>1){
        stop("y needs to be just one variable")
    }
    as.formula(        
        paste0("`",y,"`", " ~ ", x_lm_formula(x))
    )
}

# Example
df <- data.frame(
    y = c(1,4,6), 
    x1 = c(4,-1,3), 
    x2 = c(3,9,8), 
    x3 = c(4,-4,-2)
    )

# Model Specification
columns = colnames(df)
y_cols = columns[1]
x_cols = columns[2:length(columns)]
formula = build_lm_formula(x_cols, y_cols)
formula
# output
# "`y` ~ `x1` + `x2` + `x3`"

# Run Model
lm(formula = formula, data = df)
# output
Call:
    lm(formula = formula, data = df)

Coefficients:
    (Intercept)           x1           x2           x3  
        -5.6316       0.7895       1.1579           NA  

`` `

1

Sie können das Paket leaps und insbesondere die Funktionen regsubsets() Zur Modellauswahl überprüfen. Wie in der Dokumentation angegeben:

Modellauswahl durch erschöpfende Suche, schrittweises Vorwärts- oder Rückwärtsfahren oder sequentielles Ersetzen

0
amonk