【问题标题】:Regex look ahead assertion正则表达式前瞻断言
【发布时间】:2015-10-11 01:12:36
【问题描述】:

我需要一位regex 专家来解决这个问题。它与我丢失的一个 SO 问题相关联,其中数据如下:

x = c("IID:WE:G12D/V/A", "GH:SQ:p.R172W/G", "HH:WG:p.S122F/H")

我需要拆分x 的每个元素以隔离可以由letter - slash - letter - .... slash - letter 构成的末端部分。 我想要的是获得这两个向量作为输出:

o1 = c("IID:WE:G12", "GH:SQ:p.R172", "HH:WG:p.S122")
o2 = c("D/V/A", "W/G", "F/H")

我有o1 的这个解决方案:

gsub('[A-Z]/.+','',x)
#[1] "IID:WE:G12"   "GH:SQ:p.R172" "HH:WG:p.S122"

很好。对于o2,我尝试使用断言,尤其是前瞻断言:

gsub('.+(?=[A-Z]/.+)','',x, perl=T)
#[1] "V/A" "W/G" "F/H"

但这不是想要的结果!

知道第二个正则表达式出了什么问题吗?

【问题讨论】:

  • 链接到这个:stackoverflow.com/questions/31532852/string-split-and-expand-the-vector-at-the-delimiter-r? ;-)
  • 我认为这会有所帮助:gsub('.*?([^/](?:/[^/])+)$','\\1',x, perl=T)?或gsub('.*?([A-Z](?:/[A-Z])+)$','\\1',x, perl=T).
  • @CathG,是的,我发现解决方案很长,最重要的是我对正则表达式的快速限制:)
  • 所以你发布一个问题是为了回答另一个问题......有趣...... ;-)
  • 这行得通:gsub('[^/]+(?=[A-Z]/.+)','',x, perl=T)...(所以几乎是你所拥有的,只是它不起作用,因为 "\" 包含在 "." 中)

标签: regex r


【解决方案1】:

作为一种可能的解决方案,您可以使用以下替换:

gsub('.*?([^/](?:/[^/])+)$','\\1',x, perl=T)

或者(如果必须有字母):

gsub('.*?([A-Z](?:/[A-Z])+)$','\\1',x, perl=T)

IDEONE demo

  • .*? - 尽可能少地匹配除换行符以外的字符
  • ([^/](?:/[^/])+) - 捕获组匹配:
    • [^/] - / 以外的字符(或 - 如果 [A-Z] - 任何英文大写字符)
    • (?:/[^/])+ - 1 个或多个/ 序列和/ 以外的字符(或者如果您使用[A-Z],则为大写字母)。
  • $ - 字符串结束

【讨论】:

    【解决方案2】:

    试试这个:

    gsub('\\w\\/.*(\\/.*)?','',x)
    

    正则表达式向前看:

    gsub('\\w(?=\\/).*','',x,perl=T)
    
    gsub('.*\\d(?=\\w\\/)','',x, perl=T)  #For O2
    

    【讨论】:

    • o1 不需要正则表达式。
    • 我添加了正则表达式向前看。
    • 我再重复一遍:我正在寻找 o2 结果。
    【解决方案3】:

    以下,非常接近你想出的,将起作用:

    gsub('[^/]+(?=[A-Z]/.+)','',x, perl=T)

    (您的行不通,因为您要求输入“任何字符”,其中包括“\”)

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 2020-04-15
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2015-09-13
      • 2013-08-19
      • 2023-03-11
      相关资源
      最近更新 更多