You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何在R中基于每行最后两个非NA列创建新列assignation

解决方法:提取每行最后两个非NA值并拼接

你说得对,paste()确实是实现这个需求的关键工具,但我们需要先对每行的非NA值做筛选和提取,再用它来完成拼接。下面给你两种可行的实现方式:

方法一:Base R 原生实现

这种方法不需要额外安装包,直接用base R的apply()函数逐行处理:

# 先构造你的数据框
Domain <- c(rep("Bacteria",3),rep("Archaea", 2))
Phylum <- c("Proteobacteria","Cyanobacteria","Planctomycetota", "Thermoplasmatota", "Thermoplasmatota")
Class <- c("Alphaproteobacteria","Cyanobacteriia","Phycisphaerae","Poseidoniia_A",NA)
Order <- c("Sphingomonadales", NA, "Phycisphaerales", "Poseidoniales", NA)
Family <- c("Emcibacteraceae", NA, NA, "Poseidonia", NA)
Genus <- c("UBA4441", NA,NA,NA,NA)
Species <- c("UBA4441 sp", NA,NA,NA,NA)

demo_table <- data.frame(Domain, Phylum, Class, Order, Family, Genus, Species)

# 定义一个处理单行的函数:提取最后两个非NA值并拼接
get_last_two <- function(row) {
  # 筛选当前行的非NA元素
  non_na <- row[!is.na(row)]
  # 取最后两个元素,用空格拼接
  paste(tail(non_na, 2), collapse = " ")
}

# 给数据框添加新列
demo_table$assignation <- apply(demo_table, 1, get_last_two)

运行后查看结果,就会得到你想要的assignation列:

print(demo_table)

方法二:Tidyverse (dplyr) 实现

如果你习惯用tidyverse风格的代码,可以用rowwise()来逐行处理:

library(dplyr)

# 基于已有的demo_table,添加assignation列
demo_table <- demo_table %>%
  rowwise() %>%
  mutate(
    # 收集当前行所有非NA值到列表里
    non_na_vals = list(c_across(everything())[!is.na(c_across(everything()))]),
    # 提取最后两个并拼接
    assignation = paste(tail(non_na_vals, 2), collapse = " ")
  ) %>%
  ungroup() %>%
  select(-non_na_vals) # 移除临时中间列

关键逻辑解释

两种方法的核心思路是一致的:

  1. 对每行数据,先筛选出所有非NA的元素;
  2. 用tail(..., 2)提取这些元素里的最后两个;
  3. 用paste(..., collapse = " ")把这两个元素用空格连接成字符串。

这样就能完美匹配你给出的预期输出啦!

内容的提问来源于stack exchange,提问作者Valentin

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.04 10:45:28