R 从字符串中提取不规则的数字数据
我有如下数据。我希望从这里名为R 从字符串中提取不规则的数字数据,r,regex,string,R,Regex,String,我有如下数据。我希望从这里名为my.string的每个字符串中提取第一年和最后一年。有些字符串只包含一年,有些字符串不包含年。没有字符串包含超过两年的时间。我已经在示例数据集下面名为required.result的对象中提供了所需的结果。我正在使用R 当字符串包含两年时,这些年包含在字符串的一部分中,该部分如下所示ga49.51或ea22.24 当字符串仅包含一年时,该年将包含在字符串的如下部分:time11 我知道一点关于regex,但这个问题似乎太不规则和复杂了,我想不出来。我甚至不知道从哪
my.string
的每个字符串中提取第一年和最后一年。有些字符串只包含一年,有些字符串不包含年。没有字符串包含超过两年的时间。我已经在示例数据集下面名为required.result
的对象中提供了所需的结果。我正在使用R
当字符串包含两年时,这些年包含在字符串的一部分中,该部分如下所示ga49.51
或ea22.24
当字符串仅包含一年时,该年将包含在字符串的如下部分:time11
我知道一点关于regex
,但这个问题似乎太不规则和复杂了,我想不出来。我甚至不知道从哪里开始。谢谢你的建议
编辑
也许删除第一个冒号(:)之前的数字,剩下的数字就是我想要的
my.data <- read.table(text = '
my.string cov1 cov2
42:Alpha:ga6.8 -0.1 2.2
43:Alpha:ga9.11 -2.5 0.6
44:Alpha:ga30.32 -1.3 0.5
45:Alpha:ga49.51 -2.5 0.6
50:Alpha:time1:ga.time -1.7 0.9
51:Alpha:time2:ga.time -1.5 0.8
52:Alpha:time3:ga.time -1.0 1.0
2:Beta:ea2.9 -1.7 0.6
3:Beta:ea17.19 -5.0 0.8
4:Beta:ea22.24 -6.4 1.0
8:Beta:as 0.2 0.6
9:Beta:sd 1.7 0.4
12:Beta:time1:ea.tim -2.6 1.8
13:Beta:time10:ea.ti -3.6 1.1
14:Beta:time11:ea.ti -3.1 0.7
', header = TRUE, stringsAsFactors = FALSE, na.strings = "NA")
desired.result <- read.table(text = '
my.string cov1 cov2 time1 time2
42:Alpha:ga6.8 -0.1 2.2 6 8
43:Alpha:ga9.11 -2.5 0.6 9 11
44:Alpha:ga30.32 -1.3 0.5 30 32
45:Alpha:ga49.51 -2.5 0.6 49 51
50:Alpha:time1:ga.time -1.7 0.9 1 NA
51:Alpha:time2:ga.time -1.5 0.8 2 NA
52:Alpha:time3:ga.time -1.0 1.0 3 NA
2:Beta:ea2.9 -1.7 0.6 2 9
3:Beta:ea17.19 -5.0 0.8 17 19
4:Beta:ea22.24 -6.4 1.0 22 24
8:Beta:as 0.2 0.6 NA NA
9:Beta:sd 1.7 0.4 NA NA
12:Beta:time1:ea.tim -2.6 1.8 1 NA
13:Beta:time10:ea.ti -3.6 1.1 10 NA
14:Beta:time11:ea.ti -3.1 0.7 11 NA
', header = TRUE, stringsAsFactors = FALSE, na.strings = "NA")
my.data这里有一个正则表达式,它将提取这两种类型中的任何一种,并将它们输出到行尾的不同列:
搜索:*(?:时间(\d+)|(?:[ge]a)(\d+)\(\d+)。*
替换:$0\t$1\t$2\t$3
细分:
*(?:
…).*
确保整行匹配,并将非捕获组用于主替换
时间(\d+)
:这是交替的前半部分,捕获“时间”后的任何数字
(?:[ge]a)(\d+)\(\d+)
:交替的后半部分与“ga”或“ea”匹配,后跟两组数字,每个数字都在自己的捕获组中
- 替换:
$0
将整行放回原处。将添加其他每个捕获组,并在它们之间添加选项卡
我建议使用stringr library来提取您需要的数据,因为它可以更好地处理NA值,并且还允许使用受约束的宽度查找:
> library(stringr)
> my.data$time1 <- str_extract(my.data$my.string, "(?<=time)\\d+|(?<=\\b[ge]a)\\d+")
> my.data$time2 <- str_extract(my.data$my.string, "(?<=\\b[ge]a\\d{1,100}\\.)\\d+")
> my.data
my.string cov1 cov2 time1 time2
1 42:Alpha:ga6.8 -0.1 2.2 6 8
2 43:Alpha:ga9.11 -2.5 0.6 9 11
3 44:Alpha:ga30.32 -1.3 0.5 30 32
4 45:Alpha:ga49.51 -2.5 0.6 49 51
5 50:Alpha:time1:ga.time -1.7 0.9 1 <NA>
6 51:Alpha:time2:ga.time -1.5 0.8 2 <NA>
7 52:Alpha:time3:ga.time -1.0 1.0 3 <NA>
8 2:Beta:ea2.9 -1.7 0.6 2 9
9 3:Beta:ea17.19 -5.0 0.8 17 19
10 4:Beta:ea22.24 -6.4 1.0 22 24
11 8:Beta:as 0.2 0.6 <NA> <NA>
12 9:Beta:sd 1.7 0.4 <NA> <NA>
13 12:Beta:time1:ea.tim -2.6 1.8 1 <NA>
14 13:Beta:time10:ea.ti -3.6 1.1 10 <NA>
15 14:Beta:time11:ea.ti -3.1 0.7 11 <NA>
>库(stringr)
>my.data$time1 my.data$time2 my.data
my.string cov1 cov2 time1 time2
142:Alpha:ga6.8-0.12.2 6 8
243:Alpha:ga9.11-2.50.6911
344:Alpha:ga30.32-1.30.532
45:Alpha:ga49.51-2.50.64951
550:Alpha:time1:ga.time-1.70.91
651:Alpha:time2:ga.time-1.50.82
752:Alpha:time3:ga.time-1.01.03
82:Beta:ea2.9-1.70.62
93:Beta:ea17.19-5.0 0.8 17 19
104:Beta:ea22.24-6.41.0224
11.8:Beta:as 0.20.6
12.9:测试版:sd 1.7 0.4
13 12:Beta:time1:ea.tim-2.61.81
14 13:Beta:time10:ea.ti-3.61.110
15 14:Beta:time11:ea.ti-3.10.7 11
第一个正则表达式匹配:
(?您使用什么编程语言或脚本语言来处理文本文件?能否根据您的示例输入显示希望输出的示例?ga49.51
的哪个部分是一年?time11
的哪个部分是一年(我猜11
)(?:time | ga | ea)(?\d+)(\。(?\d+))
read.table(text=gsub('\\D+^\\D+','',my.data$my.string),fill=TRUE)
@MarkMiller抱歉,我正试图快速完成,只需添加blank.lines.skip=FALSE
,所以请尝试read.table(text=gsub('\\D+^\\D+','',my.data$my.string),fill=TRUE,blank.lines.skip=FALSE)