【问题标题】:Separating string from multiple columns in R从R中的多列中分离字符串
【发布时间】:2020-02-28 19:39:56
【问题描述】:

我有一个看起来有点像这样的数据集

Species   Trend2001   TrendLimits2001   Trend 2002   TrendLimits2002
 Dog        -1.5        -1,-1.64          -1.0         -0.56,-2.0 
 Cat         2.3         2.0,3.1           1.75          1,2.2 
 Mouse       0.65       -0.3,1.0          1.02         -0.1,1.5

我想将“TrendLimits”列拆分为两列,分别称为 LowerLimits 和 UpperLimits。我知道如何分别为每一列执行此操作,但是有没有办法让 R 根据它们存在“,”的事实来拆分所有列?在我的实际数据集中,我有 100 多列需要拆分,我不想为每一列写代码。

我希望我的数据最终的样子是

Species   Trend2001    LowerLimits2001   UpperLimits2001  Trend 2002   LowerLimits2002    UpperLimits2002
 Dog        -1.5           -1                -1.64          -1.0         -0.56                -2.0 
 Cat         2.3           2.0                3.1           1.75          1                    2.2 
 Mouse       0.65         -0.3                1.0           1.02         -0.1                  1.5

我对 R 很陌生,所以请给出详细的答案 :) 提前致谢!

【问题讨论】:

  • separate 中的tidyverse 函数也可以用于此。

标签: r multiple-columns csv


【解决方案1】:

我们可以从splitstackshape使用cSplit

library(splitstackshape)
cSplit(df1, c("TrendLimits2001", "TrendLimits2002"), sep=",")

或者使用base Rread.csv,创建列的基本名称('v1')和paste作为后缀的年份值paste0rep,然后循环遍历具有' TrendLimits' 作为列名中的子字符串,用read.csv 读取,将data.frames 的listcbind 绑定,并通过赋值更新原始数据集

v1 <- c("LowerLimits", "UpperLimits")
nm1 <- paste0(v1, rep(2001:2002, each = length(v1)))
nm2 <- grep("TrendLimits", names(df1), value = TRUE)
df1[nm1] <- do.call(cbind, lapply(df1[nm2], function(x)
     read.csv(text = as.character(x), header = FALSE)))
df1[nm2] <- NULL
df1
#  Species Trend2001 Trend2002 LowerLimits2001 UpperLimits2001 LowerLimits2002 UpperLimits2002
#1     Dog     -1.50     -1.00            -1.0           -1.64           -0.56            -2.0
#2     Cat      2.30      1.75             2.0            3.10            1.00             2.2
#3   Mouse      0.65      1.02            -0.3            1.00           -0.10             1.5

数据

df1 <- structure(list(Species = c("Dog", "Cat", "Mouse"), Trend2001 = c(-1.5, 
2.3, 0.65), TrendLimits2001 = c("-1,-1.64", "2.0,3.1", "-0.3,1.0"
), Trend2002 = c(-1, 1.75, 1.02), TrendLimits2002 = c("-0.56,-2.0", 
"1,2.2", "-0.1,1.5")), class = "data.frame", row.names = c(NA, 
-3L))

【讨论】:

  • 这仍然需要我为每个列命名。有没有一种方法可以在不命名列的情况下做到这一点?如果我使用 cSplit,我有 100 多个列需要命名
  • @CamiHurtado 在这里,我假设您的列名是 TrendLimits,因此创建基本 R 解决方案时考虑到这一点
  • 你能再解释一下吗?我不想写出每列的名称,例如c("TrendLimits2001", "TrendLimits2002"...etc) 或新的列名,例如c("LowerLimits2001", "UpperLimits2001", "LowerLimits2002", "UpperLimits2002"),你写的两个代码作为解决方案都写出来了。
  • @CamiHurtado 在第二个解决方案中,我更新了pasterep(如果你已经检查过的话)。唯一指定的是v1 &lt;- c("LowerLimits", "UpperLimits")
  • @CamiHurtado 我猜你也想删除 TrendLimits 原始列,对吧?
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多