2014-02-10 69 views
0

我有一個大型數據框,其中有多個列代表針對不同個人測量的不同變量。列的名稱始終以數字開頭(例如1:18)。我想爲df子集併爲每個人創建separete dfs。這是一個例子:基於列名的第一個字母的子集數據框

x <- as.data.frame(matrix(nrow=10,ncol=18)) 
colnames(x) <- paste(1:18, 'col', sep="") 

我的真實DF的列名是個人ID,變量名,和該措施的數量的組合物(I了每個變量的3次測量)。因此,例如我有個人1的措施b(身體),然後在df我會有3列名爲:1b1,1b2,1b3。最後我有10個不同的區域(身體,頭部,尾巴,尾巴,背部,側腹,腹部,喉嚨,前臂,腿部)。因此,對於每個人我有30列(10個區域×每個區域3個措施)。所以我有多個變量,從不同的數字開始,我想根據它們的唯一數字進行子集分析。我試着用grep:

partialName <- 1 
df2<- x[,grep(partialName, colnames(x))] 
colnames(x) 
[1] "1col" "2col" "3col" "4col" "5col" "6col" "7col" "8col" "9col" "10col" 
"11col" "12col" "13col" "14col" "15col" "16col" "17col" "18col" 

我在這裏的問題,因爲你可以看到它不會將個人分開,因爲1和10的子集。換句話說,這將選擇以1開頭的每個人。 最終,我想要做的是循環所有個人(1:18),爲每個人創建新的dfs。

+0

歡迎SO。你能否提供'colnames'並澄清你的期望? – Llopis

+0

感謝您的回覆Llopis。好。在上面的例子中,我的姓氏是:[1]「1col」「2col」「3col」「4col」「5col」「6col」「7col」「8col」「9col」「10col」「11col」「12col」「13col」 「14col」「15col」「16col」「17col」「18col」 我想返回不同的dfs子集名稱以相同數字開頭的列。在上面的例子中,我會有18個新的dfs,每個有1列,1col,2col,3cols等等。明白了嗎? – costagc

+1

@ user3293163將這些內容編輯到問題中,而不是作爲評論發佈。 –

回答

0

我認爲將數據保存在一個data.frame是最好的選擇。要麼,要麼將其放入data.frame的列表中。這可以更容易地爲每個人提取摘要統計信息。

首先創建一些示例數據:

df = as.data.frame(matrix(runif(50 * 100), 100, 50), stringsAsFactors = FALSE) 
names_variables = c('spam', 'ham', 'shrub') 
individuals = 1:100 
column_names = paste(sample(individuals, 50), 
        sample(names_variables, 50, TRUE), 
        sep = '') 
colnames(df) = column_names 

我會做的首先是使用melt從寬幅投的數據,以長格式。這實質上堆疊在一個大的載體中的所有列,並將其添加進來這列從一個額外的列有說服力:

library(reshape2) 
df_melt = melt(df) 
head(df_melt) 
    variable  value 
1 85ham 0.83619111 
2 85ham 0.08503596 
3 85ham 0.54599402 
4 85ham 0.42579376 
5 85ham 0.68702319 
6 85ham 0.88642715 

然後,我們需要的ID號從變量中分離出來。這裏的假設是變量的數字部分是個人ID,文本是變量名:

library(dplyr) 
df_melt = mutate(df_melt, individual_ID = gsub('[A-Za-z]', '', variable), 
          var_name = gsub('[0-9]', '', variable)) 

除去基本上不需要串的一部分。現在,我們可以做好事,如:

mean_per_indivdual_per_var = summarise(group_by(df_melt, individual_ID, var_name), 
             mean(value)) 
head(mean_per_indivdual_per_var) 
    individual_ID var_name mean(value) 
1   63  spam 0.4840511 
2   46  ham 0.4979884 
3   20 shrub 0.5094550 
4   90  ham 0.5550148 
5   30 shrub 0.4233039 
6   21  ham 0.4764298 
+0

親愛的Paul Hiemstra,這看起來確實不錯,但我仍然有點麻煩。首先,我需要將我的數據恢復爲原始格式(每個變量位於不同的列中)。其次,對於每個變量,我有三種不同的度量,例如63spam1,63spam2,63spam3。這會干擾individual_ID的生成,因爲63spam1變成了631.任何想法如何處理?非常感謝你的幫助。 – costagc

+0

請詳細說明您的問題,並告訴我們您在解決問題時所嘗試的內容(例如,使用我的示例代碼)。如果你想到自己的解決方案,可以編輯這個問題或問一個新問題。 –

+0

謝謝@保羅Hiemstra。我相應地更改了你的代碼。現在列名與我的原始數據具有相似的結構。他們從一個數字(個體ID)開始,然後是變量名稱(測量變量的區域),然後是另一個數字(重複)。例如,在上面的代碼中,列81shrub1(個體81,區域灌木,度量1)。我最終想要的是每個個人ID都有一個df。 – costagc

1

看來你colnames是data.frame標準的,所以得到的只是列1,你可以這樣做:

df2 <- df[,1] #Where 1 can be changed to the number of column you wish. 

有不需要通過部分名稱進行子集化。 雖然不建議您可以創建一個循環,這樣做的:

for (i in ncol(x)){ 
    assing(paste("df",i), x[,i]) #I use paste to get a different name for each column 
} 

雖然@paulhiemstra解決方案避免了循環。

因此,與新的信息,那麼你可以做你使用grep想要的,但具體告訴你有多少比賽預計有:

df2<- x[,grep("1{30}", colnames(x))] 
+0

對不起,我用了一個不好的例子來說明我的問題。在我的情況下,我不能工作,如果列號。 – costagc

+0

那麼,你真正的列名是什麼?如果你說你有三個觀察每個變量(我假設這意味着每列可以創建嵌套的數據框:包含所有數據的數據框,以及每個變量的內部數據框。但請嘗試完成你的問題,我們無法猜測所有這些問題 – Llopis

+0

我真正的df的列名是個人ID,變量名稱和度量數的組合(我對每個變量採取3個度量),例如,我有度量(身體),然後在df我會有3列名爲:1b1,1b2,1b3。最後,我有10個不同的區域(身體,頭部,尾巴,尾巴基地,背部,側面,venter,喉嚨,前臂,腿),因此對於每個人我有30列(10個區域x每個區域3個措施) – costagc

相關問題