正则表达式没有捕获所有匹配

时间:2017-05-15 06:43:27

标签: regex yaml

Regex101:https://regex101.com/r/oUbqBw/1

因此,我需要在评估者的数组中获取selectedSurvey(检查),feedbackType(检查)和每个对象的名称/电子邮件(数组可以有N个具有这些键的对象)。

从示例中可以看出,这是我在捕获组#3上得到的结果:

`John Doe","email":"john@doe.com"},{"name":"Jane Doe`

我知道这是因为我使用了贪婪的捕捉群体,但即使是非贪婪的我也无法让它发挥作用(正确地命名,但无法捕捉)电子邮件)。

3 个答案:

答案 0 :(得分:2)

正如其他人指出的那样,使用json解析器可能会更好。如果你真的必须,我会使用这个正则表达式(demo):

{
  "selectedSurvey":"([^"]+)",
  "feedbackType":"([^"]+)",
  "assessors":\[
    ((?:{"name":"([^"]*)","email":"([^"]*)"},?)*)
  ]
}/mx

说明:

  • /x开关可让您将正则表达式写入多行。即whitepsaces将被忽略,但表达式将更具可读性。
  • 我更喜欢使用否定的字符类"([^"]*)"而不是贪婪/懒惰的限定符。它说:“引用,然后捕获所有非引用字符,然后另一个引用”。只要您在属性中没有转义引号,这就没问题了。
  • 阵列有点棘手。我知道没办法用一个正则表达式捕获所有部分。可能这是不可能的。但是,此构造将允许您将它们全部匹配:\[((?:{...},?)*)]
    • {...}将匹配数组中的一个项目
    • (?:{...},?)将匹配一个项目和一个可选的逗号。即最后一个数组项后面没有逗号。我们不想捕获这个群体。我们将捕获所有重复。因此,它是一个非捕获组:(?:...)
    • ((?:{...},?)*) - 内部非捕获组有一个修饰符:*,即可以有更多这样的东西。然后,我们用一组捕获所有重复。
    • 作为奖励,最后数组项目的内容在第4组和第5组中。可能您可以忽略它们。
    • 稍后您可以split此数组并使用此正则表达式解析它们:"([^"]*)"

答案 1 :(得分:1)

yaml数据看起来像json 在javascript中,您可以使用JSON.parse来解析来自JSON的数据。

var str = '{"selectedSurvey":"Performance Survey","feedbackType":"official","assessors":[{"name":"John Doe","email":"john@doe.com"},{"name":"Jane Doe","email":"jane@doe.com"}]}';

var obj = JSON.parse(str);

console.log("selectedSurvey: "+ obj.selectedSurvey);
console.log("feedbackType : "+ obj.feedbackType);
for (var i in obj.assessors) { 
   console.log("assessor "+ i +": "+ obj.assessors[i].name+ ", " +obj.assessors[i].email); 
}

答案 2 :(得分:1)

尝试这样的事情:

(?<="selectedSurvey":")([^"]+)|(?<="feedbackType":")([^"]+)|(?<="name":")([^"]+)|(?<="email":")([^"]+)

此正则表达式包含4个备选方案,每个方案都包含:

  • 项目标题(引号),冒号和“开头”的后视图, 报价,
  • 一个捕获组,捕获除引号之外的一系列字符。

每个选项都有不同的项目标题: selectedSurvey feedbackType 名称电子邮件

由于g(全局)选项,每个“有趣”项都会被捕获 各个捕获小组的出现顺序。

因此,您捕获的示例中包含的源文本将被捕获 以下方式:

  • 捕获第1组捕获 selectedSurvey
  • 捕获第2组捕获 feedbackType
  • 捕获第3组会捕获第一个名称
  • 捕获第4组捕获第一个电子邮件
  • 捕获第3组会捕获第二个名称
  • 捕获第4组捕获第二个电子邮件