2016-09-17 58 views
-2

我想創建一個函數,允許在運行迴歸分析之前將數據框的選定列轉換爲分類數據類型(因子)。R - 從字符串獲取數據幀的列

問題是如何使用字符串(字符)從數據框中切出特定列。

例子:

strColumnNames <- "Admit,Rank" 
    strDelimiter <- "," 
    strSplittedColumnNames <- strsplit(strColumnNames, strDelimiter) 
    for(strColName in strSplittedColumnNames[[1]]){ 
    dfData$as.name(strColName) <- factor(dfData$get(strColName)) 
    } 

嘗試:

dfData$as.name() 
dfData$get(as.name()) 
dfData$get() 

錯誤消息: 錯誤:試圖將非功能

任何幫助將不勝感激!謝謝!!!

+0

我不知道打勾並感謝您的指導。看起來tick對用戶來說非常重要 - 在這裏很可怕。 – AiRiFiEd

回答

1

您需要更改

dfData$as.name(strColName) <- factor(dfData$get(strColName)) 

dfData[[strColName]] <- factor(dfData[[strColName]]) 

您可以爲更多的閱讀?"[["

就你而言,列名是編程生成的,[[]]是唯一的出路。也許這個例子就足以明確說明的$問題:

dat <- data.frame(x = 1:5, y = 2:6) 
z <- "x" 

dat$z 
# [1] NULL 

dat[[z]] 
# [1] 1 2 3 4 5 

至於其他的答案

apply肯定是不行的,因爲你申請的功能是as.factorfactorapply總是在一個矩陣上工作(如果你給它一個數據幀,它會先將它轉換成一個矩陣)並返回一個矩陣,而矩陣中不能有因子數據類。考慮這個例子:

x <- data.frame(x1 = letters[1:4], x2 = LETTERS[1:4], x3 = 1:4, stringsAsFactors = FALSE) 
x[, 1:2] <- apply(x[, 1:2], 2, as.factor) 

str(x) 
#'data.frame': 4 obs. of 3 variables: 
# $ x1: chr "a" "b" "c" "d" 
# $ x2: chr "A" "B" "C" "D" 
# $ x3: int 1 2 3 4 

注意,你仍然有字符變量而不是因子。正如我所說的,我們必須使用lapply

x[1:2] <- lapply(x[1:2], as.factor) 

str(x) 
#'data.frame': 4 obs. of 3 variables: 
# $ x1: Factor w/ 4 levels "a","b","c","d": 1 2 3 4 
# $ x2: Factor w/ 4 levels "A","B","C","D": 1 2 3 4 
# $ x3: int 1 2 3 4 

現在我們看到的因子類x1x2

對數據幀使用apply從來就不是一個好主意。如果閱讀的apply源代碼:

dl <- length(dim(X)) 
    if (is.object(X)) 
    X <- if (dl == 2L) 
     as.matrix(X) 
    else as.array(X) 

你看到的數據幀(其具有2維)將被裹挾第一至矩陣。這非常慢。如果您的數據框列有多個不同的類,則生成的矩陣將只有1個類。誰知道這種強制的結果會是什麼。

然而apply寫R中沒有C,用普通for循環:

for (i in 1L:d2) { 
     tmp <- forceAndCall(1, FUN, newX[, i], ...) 
     if (!is.null(tmp)) 
      ans[[i]] <- tmp 

所以它只不過是一個明確的for循環你寫你自己更好。

0

我會用不同的方法。

創建要改變的因素列名的載體:

factorCols <- c("Admit", "Rank") 

通過索引然後提取這些列:

myCols <- which(names(dfData) %in% factorCols) 

最後,使用適用於這些列改爲因素:

dfData[,myCols] <- lapply(dfData[,myCols],as.factor) 
+0

嘿greghk,這個方法的選擇背後有沒有什麼原因與哲源提出的?謝謝! – AiRiFiEd

+0

@ZheyuanLi你是對的,lapply對於未來的重現性會更好。我的觀點是,通過使用* apply函數而不是for循環,可以使代碼更加簡潔易懂 – greghk

+0

@ZheyuanLi我已經編輯以反映您對lapply的要求 – greghk