在 data.frame 中按组删除尾随 NA
Remove trailing NA by group in a data.frame
我有一个带有分组变量的 data.frame,值列中有一些 NA。
df = data.frame(group=c(1,1,2,2,2,2,2,3,3), value1=1:9, value2=c(NA,4,9,6,2,NA,NA,1,NA))
我可以使用 zoo::na.trim
删除列末尾的 NA:这将删除 data.frame:
的最后一行
library(zoo)
library(dplyr)
df %>% na.trim(sides="right")
现在我想按组删除尾随的NA;我如何使用 dplyr 实现此目的?
value2 列的预期输出:c(NA, 4,9,6,2,1)
使用lapply,遍历组:
do.call("rbind", lapply(split(df, df$group), na.trim, sides = "right"))
# group value1 value2
# 1.1 1 1 NA
# 1.2 1 2 4
# 2.3 2 3 9
# 2.4 2 4 6
# 2.5 2 5 2
# 3 3 8 1
或使用by,如@Henrik所述:
do.call("rbind", by(df, df$group, na.trim, sides = "right"))
您可以编写一个小辅助函数来检查向量的尾随 NA
,然后使用 group_by
和 filter
。
f <- function(x) { rev(cumsum(!is.na(rev(x)))) != 0 }
library(dplyr)
df %>%
group_by(group) %>%
filter(f(value2))
# A tibble: 6 x 3
# Groups: group [3]
group value1 value2
<dbl> <int> <dbl>
1 1 1 NA
2 1 2 4
3 2 3 9
4 2 4 6
5 2 5 2
6 3 8 1
编辑
如果我们需要删除前导零和尾随零,我们需要稍微扩展该功能。
f1 <- function(x) { cumsum(!is.na(x)) != 0 & rev(cumsum(!is.na(rev(x)))) != 0 }
给定 df1
df1 = data.frame(group=c(1,1,2,2,2,2,2,3,3), value1=1:9, value2=c(NA,4,9,NA,2,NA,NA,1,NA))
df1
# group value1 value2
#1 1 1 NA
#2 1 2 4
#3 2 3 9
#4 2 4 NA
#5 2 5 2
#6 2 6 NA
#7 2 7 NA
#8 3 8 1
#9 3 9 NA
我们得到这个结果
df1 %>%
group_by(group) %>%
filter(f1(value2))
# A tibble: 5 x 3
# Groups: group [3]
group value1 value2
<dbl> <int> <dbl>
1 1 2 4
2 2 3 9
3 2 4 NA
4 2 5 2
5 3 8 1
我有一个带有分组变量的 data.frame,值列中有一些 NA。
df = data.frame(group=c(1,1,2,2,2,2,2,3,3), value1=1:9, value2=c(NA,4,9,6,2,NA,NA,1,NA))
我可以使用 zoo::na.trim
删除列末尾的 NA:这将删除 data.frame:
library(zoo)
library(dplyr)
df %>% na.trim(sides="right")
现在我想按组删除尾随的NA;我如何使用 dplyr 实现此目的?
value2 列的预期输出:c(NA, 4,9,6,2,1)
使用lapply,遍历组:
do.call("rbind", lapply(split(df, df$group), na.trim, sides = "right"))
# group value1 value2
# 1.1 1 1 NA
# 1.2 1 2 4
# 2.3 2 3 9
# 2.4 2 4 6
# 2.5 2 5 2
# 3 3 8 1
或使用by,如@Henrik所述:
do.call("rbind", by(df, df$group, na.trim, sides = "right"))
您可以编写一个小辅助函数来检查向量的尾随 NA
,然后使用 group_by
和 filter
。
f <- function(x) { rev(cumsum(!is.na(rev(x)))) != 0 }
library(dplyr)
df %>%
group_by(group) %>%
filter(f(value2))
# A tibble: 6 x 3
# Groups: group [3]
group value1 value2
<dbl> <int> <dbl>
1 1 1 NA
2 1 2 4
3 2 3 9
4 2 4 6
5 2 5 2
6 3 8 1
编辑
如果我们需要删除前导零和尾随零,我们需要稍微扩展该功能。
f1 <- function(x) { cumsum(!is.na(x)) != 0 & rev(cumsum(!is.na(rev(x)))) != 0 }
给定 df1
df1 = data.frame(group=c(1,1,2,2,2,2,2,3,3), value1=1:9, value2=c(NA,4,9,NA,2,NA,NA,1,NA))
df1
# group value1 value2
#1 1 1 NA
#2 1 2 4
#3 2 3 9
#4 2 4 NA
#5 2 5 2
#6 2 6 NA
#7 2 7 NA
#8 3 8 1
#9 3 9 NA
我们得到这个结果
df1 %>%
group_by(group) %>%
filter(f1(value2))
# A tibble: 5 x 3
# Groups: group [3]
group value1 value2
<dbl> <int> <dbl>
1 1 2 4
2 2 3 9
3 2 4 NA
4 2 5 2
5 3 8 1