通过多个分隔符拆分字符串,同时在结果中包含运算符



如何通过比较运算符(>=<=><)拆分Start>=8.5Start< 14.5等字符串,将操作符保留在结果中?期望的产出将包括三个要素,例如:

output[1]
Start 
output[2]
>= 
output[3]
8.5

在第二个字符串的情况下:

output[1]
Start
output[2]
<
output[3]
14.5

我已经尝试过sapply(x, function(x) strsplit(x, ">=|<", perl = TRUE)),但这删除了分隔符。

您可以将strsplit与以下 PCRE 正则表达式一起使用:

strsplit(input, '(?<=[><=])(?=[^><=])|(?<=[^><=])(?=[><=])', perl = TRUE)

请参阅 IDEONE 演示和此正则表达式演示。

详情

正则表达式包含 2 个用 OR |管道符号分隔的替代项。第一部分 - (?<=[><=])(?=[^><=]) - 有 2 个零宽度断言,这些断言匹配来自已定义字符类 ([><=]) 的运算符符号与否定字符类 ([^><=]) 中定义的符号以外的符号之间的空位置。第二种替代方法匹配属于运算符类的字符以外的字符与属于运算符类的字符之间的空位置。因此,实际上,我们在运算符之前和之后匹配了 2 个位置。

基于纵梁str_match_all的替代解决方案

> library(stringr)
> input <- c("Start>=8.5","Start< 14.5","x == 4","tmp >= 7","ff =11","x<=2")
> output <- str_match_all(input, "([^=<>]*?)\s*([<>=]+)\s*(.*)")

请参阅正则表达式演示,([^=<>]*?)\s*([<>=]+)\s*(.*)模式有 3 个捕获组,它们捕获运算符(([^=<>]*?))、运算符本身(([<>=]+) )之前的部分,然后是它后面的内容((.*))。

我只是做一个全局查找所有的事情来把它放到一个数组中。
使用生成的数组对运算符 lhs/rhs 进行任何验证。


((?:<=?|>=?)|(?:(?!<=?|>=?).)+)(其中捕获组是可选的)

扩大

 (                             # (1 start)
      (?: <=? | >=? )
   |  
      (?:
           (?! <=? | >=? )
           . 
      )+
 )                             # (1 end)

这个正则表达式似乎有效

([^s<>=]*)s*(?=[><=]+)(.*)(?<=[><=])s*(.[^s<>=]*)

正则表达式演示

R 代码

input <- c("Start>=8.5","Start< 14.5","x == 4","tmp >= 7","ff =11","x<=2")
splitted<-strsplit(gsub("([^\s<>=]*)\s*(?=[><=]+)(.*)(?<=[><=])\s*(.[^\s<>=]*)", "\1 \2 \3", input, perl=T), " ")
splitted

Ideone 演示

最新更新