我希望使用stringr
包中的函数根据部分匹配替换数据中的整个字符串条目。
我尝试过的唯一方法是使用str_replace_all()
替换完全匹配项,但是当有数十种要纠正的变体时,这变得乏味且笨拙。我希望根据部分匹配项进行替换。在下面的reprex中,我直接指定了“西班牙人”和“哥伦比亚人”的变体。但是,我希望根据满足单词中“ Spa”或“ Col”的条件进行替换。
library(tidyverse)
library(stringr)
data <- c(
"Spanish",
"SPANIARD",
"Spainiard",
"Colombian",
"Columbian",
"Ecuador",
"Equador",
"Ecuadorian",
"VENEZUELAN"
)
str_replace_all(data,
c(
"Spanish" = "Spaniard",
"SPANIARD" = "Spaniard",
"Spainiard" = "Spaniard",
"Columbian" = "Colombian"
))
#> [1] "Spaniard" "Spaniard" "Spaniard" "Colombian" "Colombian"
#> [6] "Ecuador" "Equador" "Ecuadorian" "VENEZUELAN"
由reprex package(v0.2.1)于2019-05-21创建
因此str_replace_all()
的工作方式与广告宣传相符,但我正在寻找一种方法来简化tidyverse中的此过程。非常感谢您的帮助。
答案 0 :(得分:1)
一种选择是使用距离法进行部分匹配
vals <- c("Spaniard", "Equador", "Colombian", "Venezuelan")
library(stringdist)
vals[amatch(tolower(data), tolower(vals),maxDist=5)]
#[1] "Spaniard" "Spaniard" "Spaniard" "Colombian" "Colombian"
#[6] "Equador" "Equador" "Equador" "Venezuelan"
它可以通过tidyverse
工作流程进行管道传输
library(tidyverse)
tibble(v1 = data) %>%
mutate(v1 = vals[amatch(tolower(v1), tolower(vals), maxDist = 5)])
答案 1 :(得分:1)
我更喜欢使用距离度量(例如Jaro-winkler的距离或其他某种距离度量),但是它们确实有其缺点。厌倦了部分匹配可能会带来的变化。如果您要进行部分匹配,那么明智的做法是看看有什么可能。但是,您可以将case_when
与startsWith
或grepl
一起在tidyverse中进行概述:
tibble(data = data) %>%
mutate(
v1 = tolower(data),
new_name = case_when(
startsWith(v1, "spa") ~ "Spanaird",
startsWith(v1, "col") ~ "Colombian",
startsWith(v1, "eq") | startsWith(v1, "ec") ~ "Equadorian",
startsWith(v1, "ven") ~ "Venezuelan",
TRUE ~ as.character(data)))
# A tibble: 9 x 3
data v1 new_name
<chr> <chr> <chr>
1 Spanish spanish Spanaird
2 SPANIARD spaniard Spanaird
3 Spainiard spainiard Spanaird
4 Colombian colombian Colombian
5 Columbian columbian Colombian
6 Ecuador ecuador Equadorian
7 Equador equador Equadorian
8 Ecuadorian ecuadorian Equadorian
9 VENEZUELAN venezuelan Venezuelan
要查看可能的方法,您可以执行此操作(或其他一些操作):
tibble(data = data) %>%
arrange(data) %>%
count(tolower(data))