在PHP中需要有关正则表达式的帮助

时间:2010-11-10 19:10:32

标签: php html regex html-parsing

我正在尝试索引一系列共享相同格式的.html内容。

所以我得到了很多这样的行:<a href="meh">[18] blah blah blah < a...

这个想法是提取数字(18)和它旁边的文本(等等......)。此外,我知道每个符合条件的行都以">开头,以<a</p结尾。该问题源于需要将所有其他htmHTML标记保留为文本的一部分(<i><u>等。)

那么我有这样的事情:

$docString = file_get_contents("http://whatever.com/some.htm");
$regex="/\">\ [(.*?)\ ] (<\/a>)(.) *?(<)/";
preg_match_all($regex,$docString,$match);

让我们看一下$regex一秒钟。忽略它的空格,我只是把它们放在这里因为其他一些字符消失了。我指定它将以">开头。然后我在[]内进行数字处理。然后我挑出</a>。到目前为止一切都很好。

最后,我做了(.)*?(<)。这是转折点。通过保留最后一位(<),当找到下划线或斜体标记时,文本将被中断。但是,如果我放(<a|</p),结果数组最终为空。我已经尝试将其更改为仅(<a),但似乎2个字符搞乱了整个ting。

我该怎么办?我一整天都在苦苦挣扎。

3 个答案:

答案 0 :(得分:1)

PHP Tidy是你的朋友。 Don't use regexes

答案 1 :(得分:1)

/">\[(.*)\](.*)(?:<(?:a|\/p))/这样的东西似乎适合你的例子和描述。也许添加非捕获子模式呢?请提供一个反例,其中这不适合您。

虽然我同意RegEx不是解析器,但听起来你正在寻找的是常规行为字符串的一部分 - 这正是RegEx强大的目标。

答案 2 :(得分:0)

正如您所发现的,使用正则表达式解析HTML并不是一件容易的事。这是因为HTML并不是特别规则。

我建议使用XML解析器,例如PHP的DomDocument

创建一个对象,然后使用loadHTMLFile方法打开该文件。使用getElementsByTagName提取您的a代码,然后将内容解压缩为NodeValue属性。

可能看起来像

// Create a DomDocument object 
$html = new DOMDocument(); 

// Load the url's contents into the DOM 
$html->loadHTMLFile("http://whatever.com/some.htm"); 

// make an array to hold the text 
$anchors = array(); 

//Loop through the a tags and store them in an array 
foreach($html->getElementsByTagName('a') as $link) { 
    $anchors[] = $link->nodeValue;
    } 

这种XML / HTML解析器的一种替代方法是phpquery。他们页面上的文档应该很好地解释如何提取标签。如果您了解jQuery,界面可能看起来更自然。