【问题标题】:Conditionnaly split strings cells in a dataframe R有条件地拆分数据帧 R 中的字符串单元格
【发布时间】:2020-04-29 20:45:31
【问题描述】:

我有一个带有物种名称的数据集,其中一些最初使用的名称现在已经过时,因此它们被标注为“old_species***retired*** use new_species”,而正确的单元格只标注为“new_species”。以下是数据样本:

df<- data.frame(species=c("Etheostoma spectabile","Ictalurus furcatus","Micropterus salmoides","Micropterus salmoides","Ictalurus punctatus","Ictalurus punctatus","Ictalurus punctatus","Micropterus salmoides","Etheostoma olmstedi","Noturus insignis","Lepomis auritus","Lepomis auritus","Nocomis leptocephalus","Scartomyzon rupiscartes***retired***use Moxostoma rupiscartes","Lepomis cyanellus","Notropis chlorocephalus","Scartomyzon cervinus***retired***use Moxostoma cervinum","Ictalurus punctatus","Lythrurus ardens","Moxostoma pappillosum","Micropterus salmoides","Micropterus salmoides","Ictalurus punctatus"))

我试过了

sapply(strsplit(df$species, split='***retired***use', fixed = T),function(x) (x[2])))

但数据正确的单元格返回 NA,因为它们不包含拆分。 有没有办法只为实际包含它的单元格进行拆分?

【问题讨论】:

    标签: r dataframe strsplit


    【解决方案1】:

    您可以使用gsub 加上反向引用将旧名称更改为新名称:

    gsub(".*\\*\\*\\*retired\\*\\*\\*use\\s(.*)", "\\1", df$species)
    
    # [1] "Etheostoma spectabile"   "Ictalurus furcatus"      "Micropterus salmoides"   "Micropterus salmoides"  
    # [5] "Ictalurus punctatus"     "Ictalurus punctatus"     "Ictalurus punctatus"     "Micropterus salmoides"  
    # [9] "Etheostoma olmstedi"     "Noturus insignis"        "Lepomis auritus"         "Lepomis auritus"        
    # [13] "Nocomis leptocephalus"   "Moxostoma rupiscartes"   "Lepomis cyanellus"       "Notropis chlorocephalus"
    # [17] "Moxostoma cervinum"      "Ictalurus punctatus"     "Lythrurus ardens"        "Moxostoma pappillosum"  
    # [21] "Micropterus salmoides"   "Micropterus salmoides"   "Ictalurus punctatus" 
    

    解释:

    .* 任意次数后跟 ...

    \\*\\*\\*retired\\*\\*\\*use\\s ... 文字模式 ***retired***use 后跟 ...

    (.*) ... 任何次数的任何东西——这是gsub 的替换参数中的反向引用\\1 所指的捕获组

    【讨论】:

    • 工作完美。我只是想澄清一下,在这种情况下,必须在每个可能是运算符的字符之间使用双反斜杠 (\)?
    • 是的,在 R '方言'中,如果你愿意的话,像 * 这样的元字符在正则表达式中具有特殊含义(例如,在 * 的情况下,作为量词,意思是“零次或多次”),如果要按字面意思匹配,则必须用双反斜杠转义,例如,您希望匹配为星号的星号。很高兴,代码有效;)
    【解决方案2】:

    我们可以使用grep 创建一个索引,然后使用这些行进行拆分

    i1 <- grep('retired', df$species)
    df$species <- as.character(df$species)
    df$species[i1] <- sapply(strsplit(df$species[i1], "***retired***use ", 
                    fixed = TRUE), `[`, 2)
    
    df$species
    #[1] "Etheostoma spectabile"   "Ictalurus furcatus"      "Micropterus salmoides"   "Micropterus salmoides"   "Ictalurus punctatus"    
    #[6] "Ictalurus punctatus"     "Ictalurus punctatus"     "Micropterus salmoides"   "Etheostoma olmstedi"     "Noturus insignis"       
    #[11] "Lepomis auritus"         "Lepomis auritus"         "Nocomis leptocephalus"   "Moxostoma rupiscartes"   "Lepomis cyanellus"      
    #[16] "Notropis chlorocephalus" "Moxostoma cervinum"      "Ictalurus punctatus"     "Lythrurus ardens"        "Moxostoma pappillosum"  
    #[21] "Micropterus salmoides"   "Micropterus salmoides"   "Ictalurus punctatus"    
    

    或者使用带有sub的正则表达式

    df$species <- sub(".*\\*{3}retired\\*{3}use\\s+", "", df$species)
    

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 2020-06-14
      • 2021-04-01
      • 1970-01-01
      • 2019-06-09
      • 1970-01-01
      • 2018-01-22
      • 2021-02-05
      • 1970-01-01
      相关资源
      最近更新 更多