R中字符串操作

简介

Stringr中包含3个主要的函数族

  • 字符操作
  • 空格处理
  • 模式匹配

常用函数

在平常的数据分析工作中,经常要用到如下的函数

函数 操作
str_length() 获取字符串长度
str_sub() 截取字符串
str_dup() 复制字符串
str_pad() 空格填充
str_trunc() 截取字符串
str_trim() 去除空格
str_split(str, "[:,]") 拆分
str_c()
str_c()
拼接
str_detect() 检测模式是否存在
str_subset() 返回匹配的结果
str_count() 统计匹配次数
str_locate()
str_locate_all()
匹配定位
str_extract()
str_extract_all()
提取匹配结果
str_match()
str_match_all()
分组匹配
str_replace()
str_replace_all()
替换匹配结果

字符操作

你可使用 str_length() 获取字符串长度

str_length("abc")
#> [1] 3

您可以使用str_sub() 访问单个字符。 它有三个参数:字符向量,起始位置和结束位置。
结束位置可以是从第一个字符开始计数的正整数,或从最后一个字符计数的负整数。 闭区间,如果位置长于字符串,将被截断。

library("stringr")

# 字符串向量
x <- c('abcdef', 'ghijkl')
str_sub(x, 3, 3)
#[1] "c" "i"

str_sub(x, 2, -2)
#1] "bcde" "hijk"

# 字符串
str_x <- 'abcdef'
str_sub(str_x, 3, 4)
#[1] "cd"

# 修改字符串
str_sub(x, 3, 3) <- "X"
#[1] "abXdef" "ghXjkl"

# 复制字符串
str_dup(x, c(2, 3)) 
#[1] "abXdefabXdef"       "ghXjklghXjklghXjkl"
# 第一个字符串复制两遍,第二个字符串复制3遍

空格处理

str_pad() 通过在左侧,右侧或两侧添加多余的空格将字符串填充到固定长度。

# 左侧填充空格,长度10位
x <- c("abc", "defghi")
str_pad(x, 10)
#[1] "       abc" "    defghi"

str_pad(x, 10, "both")
[1] "   abc    " "  defghi  "

# 填充指定的字符 使用pad参数,注意,pad的参数只能是单个字符
str_pad(x, 10, pad = 'x')
#[1] "xxxxxxxabc" "xxxxdefghi"

str_pad() 永远不会剪裁字符串

str_pad(x, 4)
#> [1] " abc"   "defghi"

如果你想确保所有的字符串长度一样,可以结合str_pad() and str_trunc()一起使用:

x <- c("Short", "This is a long string")
x %>%
  str_trunc(10) %>%
  str_pad(10, "right")
#[1] "Short     " "This is..."

str_trim() 和 str_pad() 功能相反, 主要功能是去除头尾的空格

x <- c("  a   ", "b   ",  "   c")
str_trim(x)
#> [1] "a" "b" "c"
str_trim(x, "left")
#> [1] "a   " "b   " "c"

可以使用str_wrap() 来修改现有的空格,以便包装一段文本,使每行的长度尽可能相似。

jabberwocky <- str_c(
  "`Twas brillig, and the slithy toves ",
  "did gyre and gimble in the wabe: ",
  "All mimsy were the borogoves, ",
  "and the mome raths outgrabe. "
)
cat(str_wrap(jabberwocky, width = 40))
#> `Twas brillig, and the slithy toves did
#> gyre and gimble in the wabe: All mimsy
#> were the borogoves, and the mome raths
#> outgrabe.

模式匹配

我们在其他语言处理字符串时会经常使用正则表达式,我们来看看R中的正则用法
我们先来看个电话号码的例子

strings <- c(
  "apple", 
  "219 733 8965", 
  "329-293-8753", 
  "Work: 579-499-7527; Home: 543.355.3679"
)
phone <- "([2-9][0-9]{2})[- .]([0-9]{3})[- .]([0-9]{4})"
  1. str_detect() 检测模式是否存在,并返回一个逻辑向量,功能类似于 grepl()
# Which strings contain phone numbers?
str_detect(strings, phone)
#> [1] FALSE  TRUE  TRUE  TRUE
  1. str_subset() 返回匹配正则表达式的字符向量的元素, 功能类似于 grep()
str_subset(strings, phone)
#> [1] "219 733 8965"                          
#> [2] "329-293-8753"                          
#> [3] "Work: 579-499-7527; Home: 543.355.3679"
  1. str_count() 统计匹配的次数
str_count(strings, phone)
#> [1] 0 1 1 2
  1. str_locate() 定位模式匹配的第一个位子,并返回一个带有开始和结束列的数字矩阵
    str_locate_all() 定位所有的匹配,并返回带有开始和结束列的矩阵列表
# Where in the string is the phone number located?
(loc <- str_locate(strings, phone))
#>      start end
#> [1,]    NA  NA
#> [2,]     1  12
#> [3,]     1  12
#> [4,]     7  18
str_locate_all(strings, phone)
#> [[1]]
#>      start end
#> 
#> [[2]]
#>      start end
#> [1,]     1  12
#> 
#> [[3]]
#>      start end
#> [1,]     1  12
#> 
#> [[4]]
#>      start end
#> [1,]     7  18
#> [2,]    27  38
  1. str_extract() 提取第一个匹配到的文本,并返回字符向量
    str_extract_all() 提取所有匹配到的文本,返回一堆字符向量
# What are the phone numbers?
str_extract(strings, phone)
#> [1] NA             "219 733 8965" "329-293-8753" "579-499-7527"
str_extract_all(strings, phone)
#> [[1]]
#> character(0)
#> 
#> [[2]]
#> [1] "219 733 8965"
#> 
#> [[3]]
#> [1] "329-293-8753"
#> 
#> [[4]]
#> [1] "579-499-7527" "543.355.3679"
str_extract_all(strings, phone, simplify = TRUE)
#>      [,1]           [,2]          
#> [1,] ""             ""            
#> [2,] "219 733 8965" ""            
#> [3,] "329-293-8753" ""            
#> [4,] "579-499-7527" "543.355.3679"
  1. str_match() 分组匹配,从第一个匹配中提取匹配结果,返回一个字符矩阵,第一列返回完全匹配结果,其他列返回每组匹配结果
    str_match_all() 从所有匹配中提取匹配结果,返回一个字符矩阵列表
# Pull out the three components of the match
str_match(strings, phone)
#>      [,1]           [,2]  [,3]  [,4]  
#> [1,] NA             NA    NA    NA    
#> [2,] "219 733 8965" "219" "733" "8965"
#> [3,] "329-293-8753" "329" "293" "8753"
#> [4,] "579-499-7527" "579" "499" "7527"
str_match_all(strings, phone)
#> [[1]]
#>      [,1] [,2] [,3] [,4]
#> 
#> [[2]]
#>      [,1]           [,2]  [,3]  [,4]  
#> [1,] "219 733 8965" "219" "733" "8965"
#> 
#> [[3]]
#>      [,1]           [,2]  [,3]  [,4]  
#> [1,] "329-293-8753" "329" "293" "8753"
#> 
#> [[4]]
#>      [,1]           [,2]  [,3]  [,4]  
#> [1,] "579-499-7527" "579" "499" "7527"
#> [2,] "543.355.3679" "543" "355" "3679"
  1. str_replace() 替换第一个匹配的结果
    str_replace_all() 替换所有匹配到的结果
str_replace(strings, phone, "XXX-XXX-XXXX")
#> [1] "apple"                                 
#> [2] "XXX-XXX-XXXX"                          
#> [3] "XXX-XXX-XXXX"                          
#> [4] "Work: XXX-XXX-XXXX; Home: 543.355.3679"
str_replace_all(strings, phone, "XXX-XXX-XXXX")
#> [1] "apple"                                 
#> [2] "XXX-XXX-XXXX"                          
#> [3] "XXX-XXX-XXXX"                          
#> [4] "Work: XXX-XXX-XXXX; Home: XXX-XXX-XXXX"
  1. str_split() 分隔字符串
str_split("a-b-c", "-")
#> [[1]]
#> [1] "a" "b" "c"
  1. str_c(str_vec, collapse=",") 拼接向量
x <- c('a', 'b', 'c')
str_c(x, collapse = ',')
#[1] "a,b,c"

参考资料

posted @ 2017-03-15 20:39  段星星  阅读(1604)  评论(0编辑  收藏  举报