在R语言中将指定列的值向右移位并保留左侧NA
R语言实现数据框指定列值右移(NA保留左侧)
原始数据
首先定义并查看原始数据框:
df <- data.frame( a = c("one", "two", "three", "four", "five"), x = c("l", "m", NA, NA, "p"), y = c(NA, "b", "c", NA, NA), z = c("u", NA, "w", "x", "y"), stringsAsFactors = FALSE ) # 查看原始数据 df
输出结果:
a x y z 1 one l <NA> u 2 two m b <NA> 3 three <NA> c w 4 four <NA> <NA> x 5 five p <NA> y
需求说明
将数据框中的x、y、z列的非NA值向右移位,让NA保留在列的左侧,得到目标格式的输出。
解决方案(Base R)
通过自定义函数处理每一行的指定列,将非NA值移到右侧,NA补在左侧:
# 定义处理单行的函数 shift_right <- function(row) { target_cols <- c("x", "y", "z") # 提取当前行指定列的非NA值 non_na_vals <- na.omit(row[target_cols]) # 计算需要补充的NA数量 na_num <- length(target_cols) - length(non_na_vals) # 构造新的列值:NA在前,非NA值在后 new_col_vals <- c(rep(NA, na_num), non_na_vals) # 替换原行的指定列 row[target_cols] <- new_col_vals return(row) } # 应用函数到每一行,转换回数据框并保持原列顺序 df_result <- as.data.frame(t(apply(df, 1, shift_right)), stringsAsFactors = FALSE) df_result <- df_result[, names(df)] # 查看结果 df_result
输出结果:
a x y z 1 one <NA> l u 2 two <NA> m b 3 three <NA> c w 4 four <NA> <NA> x 5 five <NA> p y
解决方案(Tidyverse)
如果习惯使用tidyverse工具包,可通过以下代码实现:
library(dplyr) library(purrr) df_result_tidy <- df %>% rowwise() %>% mutate( # 对每行的x、y、z列整理:NA在前,非NA在后 temp = list(c(rep(NA, sum(is.na(c(x, y, z)))), na.omit(c(x, y, z)))) ) %>% unnest_wider(temp, names_sep = "") %>% # 重命名列到原名称 rename(x = temp1, y = temp2, z = temp3) %>% # 保持原列顺序 select(all_of(names(df))) # 查看结果 df_result_tidy
内容的提问来源于stack exchange,提问作者Mando
相关产品推荐
相关产品推荐

