我有在不同时间点对每个主题(id)进行重复测量的数据。我想为每个主题保留两行,时间点== 0,并且时间点最接近4。在这种情况下,行中的两个候选时间点与4的距离相等。 (3,5),我要选择最低的(3)。
如下图的“选择”列所示,带有“ x”的行将不会保留。
dat <- structure(list(id = c(172507L, 172507L, 172507L, 172525L, 172525L,
172525L, 172526L, 172526L, 172526L, 172527L, 172527L, 172527L,
172527L, 172527L), timepoint = c(0L, 2L, 6L, 0L, 4L, 5L, 0L,
5L, 2L, 2L, 3L, 5L, 6L, 0L)), class = "data.frame", row.names = c(NA,
-14L))
答案 0 :(得分:6)
我们可以用arrange
和id
来timepoint
,并为每个组选择timepoint == 0
时的第一次出现,并选择4 - timepoint
之间的最小绝对值。由于我们是按照timepoint
进行排列的,因此which.min
将选择值较低的第一个timepoint
(如果出现平局)。
library(dplyr)
dat %>%
arrange(id, timepoint) %>%
group_by(id) %>%
slice(c(which.max(timepoint == 0), which.min(abs(4- timepoint))))
# id timepoint
# <int> <int>
#1 172507 0
#2 172507 2
#3 172525 0
#4 172525 4
#5 172526 0
#6 172526 5
#7 172527 0
#8 172527 3
答案 1 :(得分:2)
您能做这样的事情吗?按距离排列,然后时间点将首先放置最小的最近值。然后,您可以使用/container2
函数获取时间点为零时的第一个值或过滤器。
<div>
<header>container1</header>
</div>
<div>
<header>container2</header>
<Page1 />
</div>
答案 2 :(得分:2)
这是data.table
解决方案。它基于每个ID的时间点为0的假设。否则,应使用which.max(timepoint == 0)
。感谢Ronak Shah的which.min方法。
编辑:已更改为match(TRUE, timepoint == 0)
,并修复了基本R方法中的一个问题。
library(data.table)
dt <- as.data.table(dat)
dt[order(timepoint),
.SD[c(match(TRUE, timepoint == 0), which.min(abs(4- timepoint)))],
by = id]
踢脚,这里是底脚R:
do.call(rbind, by(dat[order(dat$timepoint), ], dat[order(dat$timepoint), ], function(x) x[c(match(TRUE, x$timepoint == 0), which.min(abs(4-x$timepoint))),]) )
答案 3 :(得分:0)
类似的事情应该起作用:
zeros <-
dat %>%
filter(timepoint == 0) %>%
transmute(id, timepoint)
nonzeros <-
dat %>%
filter(timepoint != 0) %>%
mutate(diff = abs(timepoint - 4)) %>%
group_by(id) %>%
filter(diff == min(diff)) %>%
arrange(timepoint) %>%
slice(1) %>%
ungroup() %>%
transmute(id, timepoint)
df <-
bind_rows(zeros, nonzeros) %>%
arrange(id, timepoint)
可能有一种方法可以在一个管道中执行此操作,但是我可以更轻松地了解这种情况。