我在使用Regex提取不规则数据时遇到了困难。我尝试使用Lookhead但是当值不存在时,整个匹配返回false。数据集一直是一致的,直到我到达以RXX开头的字符。 RXX是唯一标识符(组),每组Rxx之间的数值是我想捕获的并将它们分配给组名。
Rxx值从R01到R15是随机的,字符串中可以存在1到15的所有值。
字符串值可能与
不同12*000000000**S304JB01811*8*0*8*4*4*34R0332R152~~~
12*000000000**S304JB01811*9*0*4*3*4*224R023R032R10234R1325~~~
我能够提取值并分配组名,直到我到达Rxx 我的尝试是提取值如下
S304JB0...(?<Total1>[\d]+).(?<Total2>[\d]+).(?<Total3>[\d]+).(?<Total4>[\d]+).(?<Total5>[\d]+).(?<Total6>[\d]+).(?<Total7>[\d]+)
这给了我想要的东西
Total1 `1`
Total2 `8`
Total3 `0`
Total4 `8`
Total5 `4`
Total6 `4`
Total7 `34`
捕获R03值并将其分配给Row在下面实现,但如果值R03不存在于字符串中,则整个匹配返回false
(?<Row3>(R03)[\d]+)
了解如何使这些正则表达式语句可选,允许我返回以下内容
Total1 `1`
Total2 `8`
Total3 `0`
Total4 `8`
Total5 `4`
Total6 `4`
Total7 `34`
Row1 `32`
Row15 `2`
S304JB0...(?<Total1>[\d]+).(?<Total2>[\d]+).(?<Total3>[\d]+).(?<Total4>[\d]+).(?<Total5>[\d]+).(?<Total6>[\d]+).(?<Total7>[\d]+)(?<Row3>(R03)[\d]+)(?<Row4>(R04)[\d]+) ------> (?<Row15>(R15)[\d]+)
感谢您的帮助
-Edited 感谢Jorge的快速回复
输入数据将是 12 * 000000000 ** S304JB01811 * 8 * 0 * 8 * 4 * 4 * 34R0332R152 ~~~
输出将是9个捕获的组结果
Group | Result
Total1 = 1
Total2 = 8
Total3 = 0
Total4 = 8
Total5 = 4
Total6 = 4
Total7 = 34
Row1 = 32
Row15 = 2
我的示例在下面与输入和分享 https://regex101.com/r/wG3aM3/68
希望这有助于澄清事情 d。
答案 0 :(得分:0)
我确信通过char解析char并存储每个值会更容易。
至于正则表达式问题,基本上你要做的就是创建所有组,就像你已经尝试过一样,但你也想让它们成为可选组,因为并非所有组都可以在那里。
您可以使用以下构造使组成为可选项:
(?:R01(?<Row1>\d+))?
因此,您应该添加其中一个以获取不同捕获组中的值。注意我使用的构造(?:non-capturing)
与组完全相同,但它不会创建反向引用。你可以阅读它here。
编辑:还有一件事。您使用.
来允许任何分隔符。但是,在性能方面,最好使用\D
之类的东西(除了数字之外的任何东西)。如果发生故障,它会为正则表达式引擎节省相当多的回溯步骤。
这将是整个表达式,假设Rxx
组始终是有序的。
S304JB0...(?<Total1>\d+)\D(?<Total2>\d+)\D(?<Total3>\d+)\D(?<Total4>\d+)\D(?<Total5>\d+)\D(?<Total6>\d+)\D(?<Total7>\d+)(?:R01(?<Row1>\d+))?(?:R02(?<Row2>\d+))?(?:R03(?<Row3>\d+))?(?:R04(?<Row4>\d+))?(?:R05(?<Row5>\d+))?(?:R06(?<Row6>\d+))?(?:R07(?<Row7>\d+))?(?:R08(?<Row8>\d+))?(?:R09(?<Row9>\d+))?(?:R10(?<Row10>\d+))?(?:R11(?<Row11>\d+))?(?:R12(?<Row12>\d+))?(?:R13(?<Row13>\d+))?(?:R14(?<Row14>\d+))?(?:R15(?<Row15>\d+))?