Php 括号之间的正则表达式文本

Php 括号之间的正则表达式文本,php,regex,nested,Php,Regex,Nested,我有一个问题,我不知道如何解决这个问题,如果正则表达式是最好的方法。 我的想法是在文件中获取函数的名称、变量和内容。 这是我的正则表达式: preg_match_all('/function (.*?)\((.*?)\)(.*?)\{(.*?)\}/s',$content,$funcs,PREG_SET_ORDER); 我有一个测试文件: function testfunc($text) { if ($text) { return 1; } return 0; } 当然,我将在

我有一个问题,我不知道如何解决这个问题,如果正则表达式是最好的方法。 我的想法是在文件中获取函数的名称、变量和内容。 这是我的正则表达式:

preg_match_all('/function (.*?)\((.*?)\)(.*?)\{(.*?)\}/s',$content,$funcs,PREG_SET_ORDER);  
我有一个测试文件:

function testfunc($text)
{

if ($text)
{
    return 1;
}
return 0;
}
当然,我将在返回0之前获取所有内容,直到“}”; 是否有一种方法可以获取函数中的所有内容,以便找到正确的“}”。

一般来说不是这样,(当然,您可以为两级深度解析定义一个正则表达式,类似于
函数(.*)(.*)(.*)(.*)(.*){([^}]*(\{[^}]*\})*\}
,但由于您可以任意深度嵌套此类结构,最终将耗尽正则表达式:D)。要做到这一点,需要上下文无关语法

您可以使用Yacc、Bison、Gppg等生成这样的语法分析器

此外,您不需要声明
*?
*
表示零次或多次,
+
表示一次或多次。

一般不需要,(您当然可以为两级深度解析定义一个正则表达式,类似于
函数(.*)(.*)(.*)\{([^}]*(\{[^}]*})*)\}
但由于可以将此类结构嵌套任意深,最终将耗尽regex:D)。要做到这一点,需要上下文无关语法

您可以使用Yacc、Bison、Gppg等生成这样的语法分析器


此外,您不需要声明
*?
*
表示零次或多次,
+
表示一次或多次。

正则表达式不是该工作的最佳工具。解析器是

毫无疑问,您可以使用regexp回调来最终管理您想要的内容,但这将是非常混乱和脆弱的


解析器可以轻松地完成同样的工作。更好的是,如果您打算用PHP解析PHP,可以使用Zend解析器来完成这项工作。

正则表达式不是完成这项工作的最佳工具。解析器是

毫无疑问,您可以使用regexp回调来最终管理您想要的内容,但这将是非常混乱和脆弱的

解析器可以轻松地完成同样的工作。更好的是,如果您计划用PHP解析PHP,可以使用Zend解析器来完成这项工作

是否有办法获取函数中的所有内容,以便找到正确的“}”

简短回答:没有

长答覆: 这不能用一个表达式来处理<代码>{和
}
也可以出现在方法体中,因此很难找到正确的结尾
}
。您需要处理(迭代或递归)所有
{}
对,并手动排序前面有“方法名”的所有对

然而,这也不简单,因为您需要排除所有看起来像函数但在方法体内有效的语句

我不认为,正则表达式是完成这样一项任务的方式。即使您能够创建所有必需的正则表达式模式,与任何专用解析器相比,性能也会更差

是否有办法获取函数中的所有内容,以便找到正确的“}”

简短回答:没有

长答覆: 这不能用一个表达式来处理<代码>{和
}
也可以出现在方法体中,因此很难找到正确的结尾
}
。您需要处理(迭代或递归)所有
{}
对,并手动排序前面有“方法名”的所有对

然而,这也不简单,因为您需要排除所有看起来像函数但在方法体内有效的语句


我不认为,正则表达式是完成这样一项任务的方式。即使您能够创建所有必需的正则表达式模式,与任何专用解析器相比,性能也会更差。

与许多观点相反,PHP(PCRE)有一种称为的东西,可以让您找到匹配的嵌套方括号。考虑这个代码:

$str = <<<'EOF'
function testfunc($text) {
   if ($text) {
       return 1;
   }
   return 0;
}
EOF;

if ( preg_match('/ \{ ( (?: [^{}]* | (?0) )+ ) \} /x', $str, $m) )
   echo $m[0];
更新:要捕获函数名和参数,请尝试以下代码:
在线演示:与许多人的想法相反,PHP(PCRE)有一个名为的东西,可以让您找到匹配的嵌套括号。考虑这个代码:

$str = <<<'EOF'
function testfunc($text) {
   if ($text) {
       return 1;
   }
   return 0;
}
EOF;

if ( preg_match('/ \{ ( (?: [^{}]* | (?0) )+ ) \} /x', $str, $m) )
   echo $m[0];
更新:要捕获函数名和参数,请尝试以下代码:
在线演示:如果你想正确地完成这项工作和/或将其扩展到更广泛使用的东西,你需要使用或创建你自己的“函数解析器”。如果你想正确地完成这项工作和/或将其扩展到更广泛使用的东西,你需要使用或创建你自己的“函数解析器”.我不想和regexp狂热者开战,但基于regexp的解析器非常脆弱,维护起来非常困难。这个regexp根本不可读。我的意思是,如果你不是每天都深入雷吉普,我怀疑如果你6个月后再看它,你能理解它的作用。此外,每一个新的解析器功能都需要更复杂的正则表达式,你很快就会陷入晦涩难懂的代码中。若要求很小,一次性的抓取这些内容来做其他事情,那个么正则表达式就可以了。然而,对于更大的工作来说,一个成熟的解析器应该是首选,尽管语言解析器也不是那么容易集成。同意,但是如果您从regexp开始,您就没有太多的改进空间。我宁愿将regexp用于优化,而不是用于初始开发。我也同意解析器不容易使用,但它们给了我们更多的自由来适应和修改设计。检查更新部分。Genius!非常感谢;)我不想与regexp狂热者开战,但基于regexp的解析器非常脆弱,维护起来非常困难。这个regexp根本不可读。我的意思是,如果你不是每天都深入雷吉普,我怀疑如果你6个月后再看它,你能理解它的作用。此外,每个新的解析器功能都需要更复杂的
$str = <<<'EOF'
function testfunc($text) {
   if ($text) {
       return 1;
   }
   return 0;
}
EOF;
if ( preg_match('/ (function [^{]+ ) ( \{ (?: [^{}]* | (?-1) )* \} ) /x', $str, $m) )
   print_r ($m);
Array
(
    [0] => function testfunc($text) {
   if ($text) {
       return 1;
   }
   return 0;
}
    [1] => function testfunc($text) 
    [2] => {
   if ($text) {
       return 1;
   }
   return 0;
}
)