牛骨文教育服务平台(让学习变的简单)
博文笔记

匹配json字符串的正则表达式

创建时间:2017-03-24 投稿人: 浏览次数:10131

在处理日志时, 发现文本里夹杂有json字符串, 希望能准确提取出来. 于是就有了下面这个正则表达式:

(?<json>(?:{s*"(?:\"|[^"])+"s*:s*(?:(?P>json)|"(?:\"|[^"])+"|[-+]?(0|[1-9]d*)(?:.[-+]?(0|[1-9]d*))?(?:[eE][-+]?(0|[1-9]d*))?|(?:true|false)|null)(?:s*,s*"(?:\"|[^"])+"s*:s*(?:(?P>json)|"(?:\"|[^"])+"|[-+]?(0|[1-9]d*)(?:.[-+]?(0|[1-9]d*))?(?:[eE][-+]?(0|[1-9]d*))?|(?:true|false)|null))*s*}|[s*(?:(?P>json)|"(?:\"|[^"])+"|[-+]?(0|[1-9]d*)(?:.[-+]?(0|[1-9]d*))?(?:[eE][-+]?(0|[1-9]d*))?|(?:true|false)|null)(?:s*,s*(?:(?P>json)|"(?:\"|[^"])+"|[-+]?(0|[1-9]d*)(?:.[-+]?(0|[1-9]d*))?(?:[eE][-+]?(0|[1-9]d*))?|(?:true|false)|null))*s*]))

匹配规则完全符合官网规范说明 http://www.json.org
生成正则时得益于两种思想: 分而治之和递归
以下是生成正则的代码和简单的测试.

<?php
function json_reg() {
    echo "<xmp>";

    //基础元素
    $r_int   = "-?d+"; //整数: 100, -23
    $r_blank = "s*"; //空白
    $r_obj_l = "\{".$r_blank; // {
    $r_obj_r = $r_blank."\}"; // }
    $r_arr_l = "\[".$r_blank; // [
    $r_arr_r = $r_blank."\]"; // [
    $r_comma = $r_blank.",".$r_blank; //逗号
    $r_colon = $r_blank.":".$r_blank; //冒号

    //基础数据类型
    $r_str   = ""(?:\\"|[^"])+"";  //双引号字符串
    $r_num   = "{$r_int}(?:\.{$r_int})?(?:[eE]{$r_int})?"; //数字(整数,小数,科学计数): 100,-23; 12.12,-2.3; 2e9,1.2E-8
    $r_bool  = "(?:true|false)"; //bool值
    $r_null  = "null"; //null

    //衍生类型
    $r_key = $r_str; //json中的key
    $r_val = "(?:(?P>json)|{$r_str}|{$r_num}|{$r_bool}|{$r_null})"; //json中val: 可能为 json对象,字符串,num, bool,null
    $r_kv  = "{$r_key}{$r_colon}{$r_val}"; //json中的一个kv结构

    $r_arr = "{$r_arr_l}{$r_val}(?:{$r_comma}{$r_val})*{$r_arr_r}"; //数组: 由val列表组成
    $r_obj = "{$r_obj_l}{$r_kv}(?:{$r_comma}{$r_kv})*{$r_obj_r}";   //对象: 有kv结构组成

    $reg = "/(?<json>(?:{$r_obj}|{$r_arr}))/is";  //数组或对象
    echo $reg, "
"; //最终正则表达式

    //以下是测试

    $str = "
  {
      "_in"dex" : "log_idx",
      "_type" : "test",
      "_id" : "1",
      "_version" : 1,
      "_shards" : {
         "total" : 2,
         "successful" : 1.3,
         "successful0" : -1.3,
         "successful2" : 1.3e-3,
         "successful4" : 1.3E3,
         "failed" : 0
      },
      "created" : true
   }";


    preg_match_all($reg, $str, $arr);
    print_r($arr);

}

//调用函数执行
json_reg();
声明:该文观点仅代表作者本人,牛骨文系教育信息发布平台,牛骨文仅提供信息存储空间服务。