2017-09-25 89 views
3

所以我有一组数据,看起来像这样一个新的变量:使用while循环来创建基于重复值中的R

group ID 
aa  123 
ab  123 
bb  345 
bb  345 
bb  999 
bb  999 
cc  567 
cd  567 

当ID是相同的,该组应该等于该ID的第二个条目。所以更正的数据应该是这样的:

group ID group2 
aa  123 ab 
ab  123 ab 
bb  345 bb 
bb  345 bb 
bb  999 bb 
bb  999 bb 
cc  567 cd 
cd  567 cd 

我还需要创建一个新的变量来存储正确的组。这是我一直在努力:

n <- 1 + (1:(as.numeric(nrow(data)))) 
l <- 1:(as.numeric(nrow(data))) 
while (data[n,1] == data[l,1]) { data$group2 <- data[n,1] } 

回答

2

假设你group列是一个字符,而不是一个因素,使用dplyr包下面的技巧将主要工作:

library(dplyr) 
answer = data %>% mutate(group2 = ifelse(ID == lead(ID), lead(group), group)) 

我说:“主要是工作”因为最后一个项目的group2值为NA。这是很容易固定,但:

answer$group2[nrow(answer)] = answer$group[nrow(answer)] 
+0

谢谢你,这工作完美!我知道必须有一个简单的方法来做到这一点。 – cwbbah

+0

谢谢!如果你觉得这个答案有用,请接受它。 – lebelinoz

2

在基础R

df$group2 = df$group[ave(1:NROW(df), df$ID, FUN = max)] 
#If each ID can have more than two rows 
#and you specifically want the value from second row, use 
#df$group[ave(1:NROW(df), df$ID, FUN = function(x) x[2])] 
df 
# group ID group2 
#1 aa 123  ab 
#2 ab 123  ab 
#3 bb 345  bb 
#4 bb 345  bb 
#5 bb 999  bb 
#6 bb 999  bb 
#7 cc 567  cd 
#8 cd 567  cd 

你也可以使用一个for循环,但它不是真的有必要

group2 = c() 
for(x in df$ID){ 
    temp = subset(df, df$ID == x) 
    group2 = c(group2, temp$group[2]) 
} 
group2 
#[1] "ab" "ab" "bb" "bb" "bb" "bb" "cd" "cd" 

DATA

df = structure(list(group = c("aa", "ab", "bb", "bb", "bb", "bb", 
"cc", "cd"), ID = c(123L, 123L, 345L, 345L, 999L, 999L, 567L, 
567L)), .Names = c("group", "ID"), row.names = c(NA, -8L), class = "data.frame") 
3

以下是使用data.table的选项。通过“ID”分组后,选择“群组”第二观察和分配(:=)到“组2”

library(data.table) 
setDT(df1)[, group2 := group[2], ID] 
df1 
# group ID group2 
#1: aa 123  ab 
#2: ab 123  ab 
#3: bb 345  bb 
#4: bb 345  bb 
#5: bb 999  bb 
#6: bb 999  bb 
#7: cc 567  cd 
#8: cd 567  cd 
+1

我们正在同一时间研究相同的解决方案。 :) – jazzurro

3

如果你想要做的一切在一个过程中,你要告诉你想要[R对于每个ID组,group的第二个元素在group2中。如果group是字符,您可以执行以下操作。您的数据被称为mydf

mydf %>% 
group_by(ID) %>% 
mutate(group2 = group[2]) 

# group ID group2 
# <chr> <int> <chr> 
#1 aa 123  ab 
#2 ab 123  ab 
#3 bb 345  bb 
#4 bb 345  bb 
#5 bb 999  bb 
#6 bb 999  bb 
#7 cc 567  cd 
#8 cd 567  cd