regex dart:使用正则表达式和包含分隔符拆分字符串

rjee0c15  于 2023-05-19  发布在  其他
关注(0)|答案(2)|浏览(167)

在Dart中,我希望使用正则表达式拆分字符串,并在结果列表中包含匹配的分隔符。因此,使用分隔符.,我希望字符串123.456.789拆分为[ 123, ., 456, ., 789 ]
在某些语言中,如C#,JavaScript,Python和Perl,根据https://stackoverflow.com/a/15668433,这可以通过简单地在捕获括号中包含分隔符来完成。这种行为似乎记录在www.example.com上https://ecma-international.org/ecma-262/9.0/#sec-regexp.prototype-@@split。
但是,这在Dart中似乎行不通:
print("123.456.789".split(new RegExp(r"(\.)")));
结果和没有括号的情况完全一样。有没有办法让split()在Dart中像这样工作?否则,我想它将不得不是一个allMatches()实现。
编辑:使用((?<=\.)|(?=\.))作为正则表达式显然可以完成单个分隔符的任务,同时具有前看和后看。我实际上会有一堆分隔符,我不确定这种方法的效率。有人能告诉我它是否可以吗?易读性当然降低了:为了允许分隔符.;,需要((?<=\.)|(?=\.)|(?<=;)(?=;))((?<=\.|;)|(?=\.|;)。测试
print("123.456.789;abc;.xyz.;ABC".split(new RegExp(r"((?<=\.|;)|(?=\.|;))")));
表明两者都在工作。

k4ymrczo

k4ymrczo1#

标准库中没有对它的直接支持,但是基于RegExp.allMatches()推出您自己的实现是相当简单的。例如:

extension RegExpExtension on RegExp {
  List<String> allMatchesWithSep(String input, [int start = 0]) {
    var result = <String>[];
    for (var match in allMatches(input, start)) {
      result.add(input.substring(start, match.start));
      result.add(match[0]!);
      start = match.end;
    }
    result.add(input.substring(start));
    return result;
  }
}

extension StringExtension on String {
  List<String> splitWithDelim(RegExp pattern) =>
      pattern.allMatchesWithSep(this);
}

void main() {
  print("123.456.789".splitWithDelim(RegExp(r"\.")));
  print(RegExp(r" ").allMatchesWithSep("lorem ipsum dolor sit amet"));
}
332nm8kg

332nm8kg2#

单分隔符拆分

给定初始字符串:

123.456.789

和预期的结果(拆分为分隔符并包括分隔符):

[123, ., 456, ., 789]

您可以使用以下正则表达式:

(?!^|$)\b

匹配与字边界匹配的位置,行的开始/结束除外。

拆分多个分隔符

现在进行编辑,给定以下字符串:

123.456.789;abc;.xyz.;ABC

您希望得到预期的结果(拆分并包括 * 多个 * 分隔符):

[123, ., 456, ., 789, ;, abc, ;, ., xyz, ., ;, ABC]

您可以使用以下正则表达式(改编自第一个添加的交替):
See regex sample here(我通过使用换行符替换来模拟拆分)。
下列工作之一。

(?!^|$)\b|(?!\w)\B(?!\w)
(?!^|$)\b|(?=\W)\B(?=\W)

# the long way (with case-insensitive matching) - allows underscore _ as delimiter
(?!^|$)(?:(?<=[a-z\d])(?![a-z\d])|(?<![a-z\d])(?=[a-z\d])|(?<![a-z\d])(?![a-z\d]))

匹配与字边界匹配的位置,行的开始/结束除外;或匹配与单词边界不匹配但前面或后面有非单词字符的位置。
注意:这将在Dart 2.3.0和更高版本中工作,因为添加了lookhind支持(更多信息请参阅此处)。

相关问题