s <- "1-343-43Hello_2_323.14_fdh-99H"
在R中,我想使用正则表达式来获取第二个下划线之前的子字符串。如何使用一个正则表达式实现这个目标?另一种方法是通过下划线进行分割,然后粘贴前两个——类似于这样的操作:
paste(sapply(strsplit(s, "_"),"[", 1:2), collapse = "_")
提供:
[1] "1-343-43Hello_2"
但是我如何编写一个正则表达式来实现相同的功能?
sub("^(([^_]*_){n}[^_]*).*", "\\1", s)
其中n
是您允许的下划线数量。
sub('\\_\\d+\\..*$','',s)
#[1] "1-343-43Hello_2"
echo preg_replace("/([^_])_([^_]).*/" , "$1_$2" , "1-343-43Hello_2_323.14_fdh-99H");
或者,如果你只是想匹配 int,那么 /^[^]*[^_]*/ 就是用来匹配它的正则表达式字符串。
<?php
echo preg_match("/^[^_]*_[^_]*/" , "1-343-43Hello_2_323.14_fdh-99H" , $test );
var_dump( $test );
?>
或者在javascript中
"1-343-43Hello_2_323.14_fdh-99H".match(/^[^_]*_[^_]*/);
如果你需要perl=TRUE(例如look-ahead和look-behind),那么在data.table中可以使用gsub进行替换,不幸的是,在str_match中无法实现。
dtx[, var_stringr := stringr::str_match(string, '([^_]+)(?:_[^_]+){5}$')[,2]][]
dtx[
# first select the ones with '_' so that the third element is NA
grepl('_', string),
var_gsub := sub('(.*_)([^_]+)(_[^_]+){5}$', '\\2', string)][]
这种方法的缺点是,如果您选择的数字高于第n个出现次数,它不会像str_match一样返回NA,而是返回整个字符串。
n
是下划线数量减1的结果,所以如果你想允许2个下划线,那么n就是1。 - G. Grothendieck