如何在 R 中用括号和数字拆分字母?
How to split letters with bracket and numbers in R?
字符串为s = '[12]B1[16]M5'
我想用 R 中的 strsplit 函数将其拆分为以下结果:
let <- c('[12]B', '[16]M')
num <- c(1, 5)
非常感谢
使用 stringr
包:
library(stringr)
x <- '[12]B1[16]M2'
let <- unlist(str_extract_all(x, "\[[0-9]{2}\][A-Z]"))
x <- gsub(pattern = "\[[0-9]{2}\][A-Z]",
replacement = "",
x)
num <- unlist(str_extract_all(x, "[0-9]"))
正则表达式"\[[0-9]{2}\][A-Z]"
可以分解为
\[
左括号
[0-9]{2}
两个连续数字的序列
\]
右括号
[A-Z]
恰好一个大写字母的序列
您可以为您的任务使用正则表达式。
s = '[12]B1[16]M22'
grx <- gregexpr("\[.+?\].+[[:digit:]]?", s)
let <- do.call(c, regmatches(s, grx))
#let
#[1] "[12]B" "[16]M"
如果你想得到所有的块(let + num),你可以调整模式如下。这有助于提取数字部分。
grx <- gregexpr("\[.+?\].+([[:digit:]]+)", s)
out <- do.call(c, regmatches(s, grx))
num <- gsub(".+\][[:alpha:]]+", "", out)
num
[1] "1" "22"
1) strapply 创建一个正则表达式,pat
匹配两个部分,然后使用 strapply
分别提取每个部分。第一个捕获组(正则表达式的第一个括号部分)由左方括号 "\["
最小字符串 ".*?"
直到右方括号 "\]"
后跟任何字符 "."
.第二个捕获组由一个或多个数字组成 "\d+"
.
library(gsubfn)
pat <- "(\[.*?\].)(\d+)"
let <- strapply(s, pat, simplify = c)
num <- strapply(s, pat, ~ as.numeric(..2), simplify = c)
let
## [1] "[12]B" "[16]M"
num
## [1] 1 5
1a) 变化
这也可以表示为 mapply
生成 2 个组件列表:
mapply(strapply, s, pat, c(~ ..1, ~ as.numeric(..2)), simplify = "c",
SIMPLIFY = FALSE, USE.NAMES = FALSE)
## [[1]]
## [1] "[12]B" "[16]M"
##
## [[2]]
## [1] 1 5
2) gsub/read.table 这不使用包——仅使用 gsub
和 read.table
。 pat
在 (1) 中定义。它 returns 一个数据框,结果在两个 coiumns 中:
read.table(text = gsub(pat, "\1 \2\n", s), as.is = TRUE, col.names = c("let", "num"))
## let num
## 1 [12]B 1
## 2 [16]M 5
3) gsub/strsplit 这有点类似于(2)但是使用strsplit
而不是read.table
。 pat
来自 (1).
spl <- matrix(strsplit(gsub(pat, "\1 \2 ", s), " ")[[1]], 2)
let <- spl[1, ]
num <- as.numeric(spl[2, ])
字符串为s = '[12]B1[16]M5'
我想用 R 中的 strsplit 函数将其拆分为以下结果:
let <- c('[12]B', '[16]M')
num <- c(1, 5)
非常感谢
使用 stringr
包:
library(stringr)
x <- '[12]B1[16]M2'
let <- unlist(str_extract_all(x, "\[[0-9]{2}\][A-Z]"))
x <- gsub(pattern = "\[[0-9]{2}\][A-Z]",
replacement = "",
x)
num <- unlist(str_extract_all(x, "[0-9]"))
正则表达式"\[[0-9]{2}\][A-Z]"
可以分解为
\[
左括号[0-9]{2}
两个连续数字的序列\]
右括号[A-Z]
恰好一个大写字母的序列
您可以为您的任务使用正则表达式。
s = '[12]B1[16]M22'
grx <- gregexpr("\[.+?\].+[[:digit:]]?", s)
let <- do.call(c, regmatches(s, grx))
#let
#[1] "[12]B" "[16]M"
如果你想得到所有的块(let + num),你可以调整模式如下。这有助于提取数字部分。
grx <- gregexpr("\[.+?\].+([[:digit:]]+)", s)
out <- do.call(c, regmatches(s, grx))
num <- gsub(".+\][[:alpha:]]+", "", out)
num
[1] "1" "22"
1) strapply 创建一个正则表达式,pat
匹配两个部分,然后使用 strapply
分别提取每个部分。第一个捕获组(正则表达式的第一个括号部分)由左方括号 "\["
最小字符串 ".*?"
直到右方括号 "\]"
后跟任何字符 "."
.第二个捕获组由一个或多个数字组成 "\d+"
.
library(gsubfn)
pat <- "(\[.*?\].)(\d+)"
let <- strapply(s, pat, simplify = c)
num <- strapply(s, pat, ~ as.numeric(..2), simplify = c)
let
## [1] "[12]B" "[16]M"
num
## [1] 1 5
1a) 变化
这也可以表示为 mapply
生成 2 个组件列表:
mapply(strapply, s, pat, c(~ ..1, ~ as.numeric(..2)), simplify = "c",
SIMPLIFY = FALSE, USE.NAMES = FALSE)
## [[1]]
## [1] "[12]B" "[16]M"
##
## [[2]]
## [1] 1 5
2) gsub/read.table 这不使用包——仅使用 gsub
和 read.table
。 pat
在 (1) 中定义。它 returns 一个数据框,结果在两个 coiumns 中:
read.table(text = gsub(pat, "\1 \2\n", s), as.is = TRUE, col.names = c("let", "num"))
## let num
## 1 [12]B 1
## 2 [16]M 5
3) gsub/strsplit 这有点类似于(2)但是使用strsplit
而不是read.table
。 pat
来自 (1).
spl <- matrix(strsplit(gsub(pat, "\1 \2 ", s), " ")[[1]], 2)
let <- spl[1, ]
num <- as.numeric(spl[2, ])