2016-05-16 64 views
2

我有一個包含組和子組的大型數據框。我想,以確定各組中的子組的索引,如示於以下數據幀的OUTPUT柱:確定子組索引

df <- data.frame(
    Group = factor(c("A","A","A","A","A","B","B","B","B")), 
    Subgroup = factor(c("a","a","b","b","b","a","a","b","b")), 
    OUTPUT = c(1,1,2,2,2,1,1,2,2) 
) 

我嘗試幾種可能性,沒有任何成功。我想與dplyr一起工作,但我不知道如何解決這個問題。以下代碼返回意外的結果。

require(dplyr) 

df <- df %>% 
    group_by(Group) %>% 
    mutate(
    OUTPUT_2 = dplyr::id(Subgroup) 
) 

#df 
# Group Subgroup OUTPUT_2 
# (fctr) (fctr) (int) 
#1  A  a  8 
#2  A  a  8 
#3  A  b  8 
#4  A  b  8 
#5  A  b  8 
#6  B  a  4 
#7  B  a  4 
#8  B  b  4 
#9  B  b  4 

我感覺我很接近,但沒有達到那裏。任何人都可以幫忙嗎?

+1

你需要這樣的東西' as.numeric(小組)'? – aosmith

回答

2

我們可以使用factor路線與dplyr

library(dplyr) 
df %>% 
    group_by(Group) %>% 
    mutate(OUTPUT = as.numeric(factor(Subgroup, levels= unique(Subgroup)))) 
# Group Subgroup OUTPUT 
# <fctr> <fctr> <dbl> 
#1  A  a  1 
#2  A  a  1 
#3  A  b  2 
#4  A  b  2 
#5  A  b  2 
#6  B  a  1 
#7  B  a  1 
#8  B  b  2 
#9  B  b  2 

或者另一種選擇通過分組之後match與「小組」的unique元素「集團」

df %>% 
    group_by(Group) %>% 
    mutate(OUTPUT = match(Subgroup, unique(Subgroup))) 
# Group Subgroup OUTPUT 
# <fctr> <fctr> <int> 
#1  A  a  1 
#2  A  a  1 
#3  A  b  2 
#4  A  b  2 
#5  A  b  2 
#6  B  a  1 
#7  B  a  1 
#8  B  b  2 
#9  B  b  2 
+1

非常好,非常感謝你!你會被接受,因爲它很簡單,實際上涉及dplyr,就像我希望它會:-) – Ratnanil

1
library(data.table) 
dt = as.data.table(df) # or setDT to convert in place 

unique(dt[, .(Group, Subgroup)])[, idx := 1:.N, by = Group][dt, on = c('Group', 'Subgroup')] 
# Group Subgroup idx OUTPUT 
#1:  A  a 1  1 
#2:  A  a 1  1 
#3:  A  b 2  2 
#4:  A  b 2  2 
#5:  A  b 2  2 
#6:  B  a 1  1 
#7:  B  a 1  1 
#8:  B  b 2  2 
#9:  B  b 2  2 

翻譯爲dplyr應該很簡單。


另一種方法,下面使用的因素來自艾歐史密斯的評論的想法,就是:

dt[, idx := as.integer(factor(Subgroup, unique(Subgroup))), by = Group][] 

這將創建一個因素,每組正確的水平,這你之後的索引。

2

這裏是一個data.table方案,不會聚集:

dt[order(Subgroup), Output := cumsum(!duplicated(Subgroup)) , by = .(Group)] 

這將與基於彙總的方法要快得多。

+0

如果子組元素四處亂動,這將不起作用 - 例如,在OP數據上改變'dt [6,Subgroup:='b']',然後再試一次 – eddi

+0

@eddi這是事實,但它很容易用'setkey'解決。 – Bulat

+2

Bulat,這是真的,但更好的辦法是讓'爲了避免重新排序(這很昂貴),'i'參數中的'order(subgroup)',它不會破壞'dt' *和*的原始順序。 – Arun