2015-10-10 3 views
3

У меня есть data.frame, который выглядит следующим образом:вычисления новый столбец на основе нескольких строк значений

Name Age Gender Team 
John 18 M  A 
Luke 75 M  B 
Dean 20 M  C 
Zoe 34 F  B 
Chloe 12 F  B 
Erik 56 M  A 

И я хотел бы, чтобы вычислить новое значение (TeamType), который будет одинаковым для всех членов команды но зависит от людей в командах.
Например, команда B имеет как M и F в команде будет иметь TeamType=Mixed тогда команды C и А будет OnlyM, как это:

Name Age Gender Team TeamType 
John 18 M  A OnlyM 
Luke 75 M  B Mixed 
Dean 20 M  C OnlyM 
Zoe 34 F  B Mixed 
Chloe 12 F  B Mixed 
Erik 56 M  A OnlyM 

Это было бы легко сделать в Python или во многих других традиционных но я не могу понять, как это сделать в R.

ответ

6

Другой dplyr подход:

library(dplyr) 
df %>% group_by(Team) %>% 
    mutate(newcol=ifelse(n_distinct(Gender) == 2, "Mixed", paste0("Only", Gender))) 
#Source: local data frame [6 x 5] 
#Groups: Team [3] 
# 
# Name Age Gender Team newcol 
# (fctr) (int) (fctr) (fctr) (chr) 
#1 John 18  M  A OnlyM 
#2 Luke 75  M  B Mixed 
#3 Dean 20  M  C OnlyM 
#4 Zoe 34  F  B Mixed 
#5 Chloe 12  F  B Mixed 
#6 Erik 56  M  A OnlyM 

я пошел по другому пути, чем jeremycg. В случае всей женской команды мы должны вставить «Только» с присутствующим полу.

база R

В base R это по существу то же самое:

with(df, ave(Gender, Team, 
      FUN=function(x) { 
       ifelse(length(unique(x)) == 2, "Mixed", paste0("Only", x))})) 
+0

Ваш подход кажется правильным, когда в группе есть только «Женщина». BTW, вы можете использовать 'n_distinct' из' dplyr' для замены 'length (unique' – akrun

+1

Спасибо. @akrun –

+0

Зачем нужна' unique (Gender) '? Если' n_distinct (Gender) <2' будет только один «пол» типа № –

7

Мы можем использовать data.table. Мы преобразуем «data.frame» в «data.table» (setDT(df1)), сгруппированные по команде «Team», if. Длина уникальных элементов «Пол» больше 1 (uniqueN(Gender)>1), мы называем это «Смешанным» или else we paste строка 'Only' с первым элементом 'Gender' (или unique элемент 'Gender'). Обратите внимание, что если есть только «F» для «Team», это даст «OnlyF».

library(data.table)#v1.9.6+ 
setDT(df1)[, TeamType:=if(uniqueN(Gender)>1) 'Mixed' 
        else paste0('Only',Gender[1L]) , by=Team] 
df1 
# Name Age Gender Team TeamType 
#1: John 18  M A OnlyM 
#2: Luke 75  M B Mixed 
#3: Dean 20  M C OnlyM 
#4: Zoe 34  F B Mixed 
#5: Chloe 12  F B Mixed 
#6: Erik 56  M A OnlyM 
+0

Спасибо за вашу помощь @akrun. Будет работать и для меня, но я нахожу подход 'dplyr' более интуитивным. В любом случае, я проголосовал за вас. – Mathiou

2

Вы можете использовать dplyr. Здесь вы группируетесь в подгруппы каждого уровня команды, затем используйте mutate, чтобы добавить столбец - «teamtype» с требуемым выходом.

library(dplyr) 
data %>% group_by(Team) %>% 
     mutate(teamtype = ifelse(all(Gender=="M"), "OnlyM", "Mixed")) 

Source: local data frame [6 x 5] 
Groups: Team [3] 

    Name Age Gender Team teamtype 
    (fctr) (int) (fctr) (fctr) (chr) 
1 John 18  M  A OnlyM 
2 Luke 75  M  B Mixed 
3 Dean 20  M  C OnlyM 
4 Zoe 34  F  B Mixed 
5 Chloe 12  F  B Mixed 
6 Erik 56  M  A OnlyM 
+0

Спасибо за помощь! – Mathiou

+1

Я не знаю, почему этот голос не получил больше голосов, чем другие. Peeps должен быть scrollin ' –

+1

@RichardScriven. Каким будет результат, когда Пол является только «F» для конкретной команды? – akrun