[英]Split a column in R with inconstant data format
我有一个有 17 列的 R dataframe。 一列包含我将用于与其他数据框合并的唯一标识符。 但是,此列中的某些行包含额外的数据,导致无法合并。 这是我正在查看的不同类型数据的子集。
M2017013708-MN-M02199-180405
M201701492756-MN-M05144-180419
M2016019446_S3_L001
M2016019762
-MN 之后的所有数据都被认为是需要删除的额外数据。 我的目标是在没有额外数据的情况下向 dataframe 添加一个新列。 它看起来像这样:
M2017013708
M201701492756
M2016019446_S3_L001
M2016019762
我试图在 -MN 处拆分数据,该列表创建一个列表,然后使用 ldply 将其放入 dataframe 中。 但是,这会导致错误,因为拆分会导致多个长度的列表,因为并非所有行都有 -MN。
split_my_data <- strsplit(my_data$sample_name, '-MN')
df <- ldply(split_my_data)
我尝试使用带有 sql 和 sqldf 的 case 和正则表达式。 但是,我收到没有这样的 function REGEXP 的错误。
任何帮助将不胜感激。
或者您可以使用Look Beind Regex (?<=)尝试此方法
df <- data.frame(OBS = 1:4,
CODE = c("M2017013708-MN-M02199-180405",
"M201701492756-MN-M05144-180419",
"M2016019446_S3_L001",
"M2016019762"))
df2 <- df %>%
mutate(CODE2 = str_replace_all(CODE, regex("(?<=)-MN.*"), ""))
# OBS CODE CODE2
# 1 1 M2017013708-MN-M02199-180405 M2017013708
# 2 2 M201701492756-MN-M05144-180419 M201701492756
# 3 3 M2016019446_S3_L001 M2016019446_S3_L001
# 4 4 M2016019762 M2016019762
一个简单整洁的解决方案也可以是:
library(dplyr)
library(stringr)
data <- tibble(dirty = c('M2017013708-MN-M02199-180405',
'M201701492756-MN-M05144-180419',
'M2016019446_S3_L001',
'M2016019762'))
data %>%
mutate(clean = str_remove(dirty, pattern = '-MN.*'))
# A tibble: 4 x 2
dirty clean
<chr> <chr>
1 M2017013708-MN-M02199-180405 M2017013708
2 M201701492756-MN-M05144-180419 M201701492756
3 M2016019446_S3_L001 M2016019446_S3_L001
4 M2016019762 M2016019762
关于 SQLite,正则表达式只有在 SQLite 构建时打开正则表达式支持时才可用,但 RSQLite 没有这样做,因此它不可用。
您可以做的是 append -MN-
到每个字符串的末尾,以确保始终至少出现一次,然后使用instr
搜索它并使用 substring 到该点使用substr
:
library(sqldf)
sqldf("select V1, substr(V1, 1, instr(V1 || '-MN-', '-MN-') - 1) as V2 from DF")
给予:
V1 V2
1 M2017013708-MN-M02199-180405 M2017013708
2 M201701492756-MN-M05144-180419 M201701492756
3 M2016019446_S3_L001 M2016019446_S3_L001
4 M2016019762 M2016019762
如果我们使用 H2 后端到 sqldf 而不是 SQLite 那么我们可以使用正则表达式。 RH2 package 包括 R 驱动程序和 H2 本身,如果加载了 sqldf 将假定您想使用它而不是 Z497757A9C5B2EC17DED656170B51C788。 加载 RH2 和 sqldf 的顺序无关紧要。
library(RH2)
library(sqldf)
sqldf("select V1, regexp_replace(V1, '-MN-.*', '') as V2 from DF")
可重现形式的输入是:
DF <- data.frame(V1 = c("M2017013708-MN-M02199-180405",
"M201701492756-MN-M05144-180419",
"M2016019446_S3_L001",
"M2016019762"))
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.