Python RegEx跳过前几个字符?

时间:2009-10-25 13:13:54

标签: python regex html-parsing

嘿,我有一个关于正则表达式的相当基本的问题。我想只返回body(包括)body标签中的文本,我知道以下是不对的,因为它也会匹配开始body标签之前的所有字符。我想知道你怎么去跳过那些?

x = re.match('(.*<body).*?(</body>)', fileString)

谢谢!

6 个答案:

答案 0 :(得分:9)

我不知道Python,但是这是一个使用Beautiful Soup一起抛出的快速示例,我经常看到建议用于Python HTML解析。

import BeautifulSoup

soup = BeautifulSoup(fileString)

bodyTag = soup.html.body.string

那将(理论上)处理HTML的所有复杂性,这对于纯正则表达式的答案来说非常困难,因为它不是正则表达式的设计目的。

答案 1 :(得分:2)

以下是一些使用正则表达式查找<body>...</body>标记之间所有文本的示例代码。虽然这演示了python的re模块的一些功能,但请注意Beautiful Soup模块非常易于使用,如果您计划解析HTML或XML,它是一个更好的工具。 (有关如何使用BeautifulSoup解析此问题的示例,请参见下文。)

#!/usr/bin/env python
import re

# Here we have a string with a multiline <body>...</body>
fileString='''baz<body>foo
baby foo
baby foo
baby foo
</body><body>bar</body>'''

# re.DOTALL tells re that '.' should match any character, including newlines.
x = re.search('(<body>.*?</body>)', fileString, re.DOTALL)
for match in x.groups():
    print(match)
# <body>foo
# baby foo
# baby foo
# baby foo
# </body>

如果您希望收集所有比赛,可以使用re.findall:

print(re.findall('(<body>.*?</body>)', fileString, re.DOTALL))
# ['<body>foo\nbaby foo\nbaby foo\nbaby foo\n</body>', '<body>bar</body>']

如果您计划多次使用此模式,可以预先编译它:

pat=re.compile('(<body>.*?</body>)', re.DOTALL)
print(pat.findall(fileString))
# ['<body>foo\nbaby foo\nbaby foo\nbaby foo\n</body>', '<body>bar</body>']

以下是使用BeautifulSoup的方法:

#!/usr/bin/env python
from BeautifulSoup import BeautifulSoup

fileString='''baz<body>foo
baby foo
baby foo
baby foo
</body><body>bar</body>'''
soup = BeautifulSoup(fileString)
print(soup.body)
# <body>foo
# baby foo
# baby foo
# baby foo
# </body>

print(soup.findAll('body'))
# [<body>foo
# baby foo
# baby foo
# baby foo
# </body>, <body>bar</body>]

答案 2 :(得分:0)

您无法使用正则表达式解析HTML。 HTML不是常规语言。请使用像lxml这样的HTML解析器。

答案 3 :(得分:-2)

 x = re.match('.*(<body>.*?</body>)', fileString)

考虑使用minidom进行HTML解析。

答案 4 :(得分:-2)

x = re.search('(<body>.*</body>)', fileString)
x.group(1)

比匹配答案少打字

答案 5 :(得分:-2)

你的fileString是否包含多行?在这种情况下,您可能需要指定它或明确跳过这些行:

x = re.match(r"(?:.|\n)*(<body>(?:.|\n)*</body>)", fileString)

或更简单地使用re模块:

x = re.match(r".*(<body>.*</body>)", fileString, re.DOTALL)
如果x不是None,

x.groups()[0]应包含您的字符串。