当模式作为数据帧中的列出现时,stringr::str_replace 函数出现问题

问题描述 投票:0回答:1

我需要将以下值替换为数据框中相应的向量元素。

a 列:c("abc*^!", "abcde+", "abcde123********++++++", "TCZ 后 6 小时 (+-3 小时)")

b 列:c('xx', 'yy', 'zz', 'aa')

如果我直接使用 stringr::str_replace_all 函数执行此操作,则它不起作用,因为列 a 中存在的 * 和 + 符号被视为正则表达式模式。为了实现这一目标,我创建了一个转义特殊字符的函数,以确保模式匹配按预期工作,字符串替换也是如此。看起来 str_replace 不喜欢从数据框中的列读取模式。有没有办法实现这个目标?

注意:我使用此方法来延续现有代码,因为它存在于 git 中并被许多其他团队使用。

以下证据表明,由 escape_spl_chars 函数创建的正则表达式模式(列 VISIT_INSTACE1)正在为 a 列创建正确的匹配模式。如果有人可以解释这一点,请告诉我。

enter image description here

x <- data.frame(a = c("abc*^!", "abcde+", "abcde123********++++++", "Post TCZ 6 hours (+-3hrs)"),
                b = c('xx', 'yy', 'zz', 'aa'), stringsAsFactors = F)

escape_spl_chars <- function(arg1){
  
  return_x <- sapply(strsplit(arg1, "", fixed = TRUE), function(y) {
    pasted_chars <- sapply(y, function(char) {
      # Convert character to ASCII code
      ascii_code <- as.integer(charToRaw(char))
      
      # Check if it's a special character and escape it
      if ((ascii_code >= 33 & ascii_code <= 47) | 
          (ascii_code >= 58 & ascii_code <= 64) | 
          (ascii_code >= 91 & ascii_code <= 96) | 
          (ascii_code >= 123 & ascii_code <= 126)) {
        return(paste0("\\\\", char))  # Escape special character
      } else if (ascii_code == 32){
        return(paste0("\\\\", 's')) # Escape space character
      } else {
        return(char)  # Return normal character
      }
    })
    
    # Collapse the characters back into a single string
    paste0(pasted_chars, collapse = "")
  })
  
  return(return_x)
  
}

x1 <- x %>% mutate(VISIT_INSTACE1 = escape_spl_chars(a))

x1 <- x1 %>% dplyr::mutate(newvisitcode = stringr::str_replace_all(a, stringr::str_trim(VISIT_INSTACE1), b))
r stringr
1个回答
0
投票

使用

fixed
比较文字字符。

library(stringr)
library(dplyr)

x %>% mutate(newvisitcode=str_replace_all(string=a, pattern=fixed(a), replacement=b))

                          a  b newvisitcode
1                    abc*^! xx           xx
2                    abcde+ yy           yy
3    abcde123********++++++ zz           zz
4 Post TCZ 6 hours (+-3hrs) aa           aa
© www.soinside.com 2019 - 2024. All rights reserved.