Python pyparsing-解析xml注释

Python pyparsing-解析xml注释,python,grammar,xml-comments,pyparsing,Python,Grammar,Xml Comments,Pyparsing,我需要解析一个包含xml注释的文件。具体来说,它是一个使用MS//约定的c文件 从这里我需要拉出foobar,或者///foobar也可以接受。(注意-如果将xml全部放在一行中,这仍然不起作用…) 但我并没有在跨多行的语法工作中取得多大成功 (注意——我在Python3.2中测试了上述示例;它可以工作,但(根据我的问题)不打印任何值) 谢谢 我认为Literal('\n')是你的问题。您不希望构建带有空格字符的文本(因为文本在尝试匹配之前默认跳过空格)。尝试改用LineEnd() 编辑1: 仅

我需要解析一个包含xml注释的文件。具体来说,它是一个使用MS
//
约定的c文件

从这里我需要拉出
foobar
,或者
///foobar
也可以接受。(注意-如果将xml全部放在一行中,这仍然不起作用…)

但我并没有在跨多行的语法工作中取得多大成功

(注意——我在Python3.2中测试了上述示例;它可以工作,但(根据我的问题)不打印任何值)

谢谢

我认为
Literal('\n')
是你的问题。您不希望构建带有空格字符的文本(因为文本在尝试匹配之前默认跳过空格)。尝试改用
LineEnd()

编辑1: 仅仅因为您得到一个带有LineEnd的无限循环并不意味着Literal('\n')更好。尝试在
\u eol
定义的末尾添加
.setDebug()
,您会发现它与任何内容都不匹配

不要试图将你的评论主体定义为“一行或多行不是结束行,而是把所有内容都放到行尾”,如果你只是:

xmlComment = _cPoundOpenXmlComment + pp.SkipTo(_cPoundCloseXmlComment) + _cPoundCloseXmlComment 

(使用LineEnd()获得无限循环的原因是,您实际上是在执行一个或多个(SkipTo(LineEnd()),但从未使用LineEnd(),因此,由于解析位置位于行的末尾,所以一个或多个只会不断匹配、匹配、解析和返回空字符串。)使用
nestedExpr
怎么样:

import pyparsing as pp

text = '''\
///<summary>
/// foobar
///</summary>
blah blah
///<summary> /// bar ///</summary>
///<summary>  ///<summary> /// baz  ///</summary> ///</summary>    
'''

comment=pp.nestedExpr("///<summary>","///</summary>")
for match in comment.searchString(text):
    print(match)
    # [['///', 'foobar']]
    # [['///', 'bar']]
    # [[['///', 'baz']]]
将pyparsing导入为pp
文本='''\
///
///福巴
///
废话
//////巴///
////////baz///
'''
注释=pp.nestedExpr(“///”,“//”)
对于注释中的匹配。搜索字符串(文本):
打印(匹配)
#[['//','foobar']]
#['//','bar']]
#[['//','baz']]

您可以使用xml解析器来解析xml。提取相关评论行应该很容易:

import re
from xml.etree import cElementTree as etree

# extract all /// lines
lines = re.findall(r'^\s*///(.*)', text, re.MULTILINE)

# parse xml
root = etree.fromstring('<root>%s</root>' % ''.join(lines))
print root.findtext('summary')
# -> foobar
重新导入
从xml.etree导入cElementTree作为etree
#提取所有///行
lines=re.findall(r'^\s*//(.*),文本,re.MULTILINE)
#解析xml
root=etree.fromstring(“%s”%'.join(行))
打印root.findtext(“摘要”)
#->foobar

谢谢你的建议;但是,更改为
\u eol=pp.LineEnd().suppress()
会导致挂起/inf循环。你能说得更具体一点吗(注意-将3个部分粘贴在一个.py文件中,代码按原样运行)。谢谢,Mikevote,请你解释一下问题所在。哼!我应该看到,我从来没有消耗过这一行的结尾:)我认为你在《银翼杀手》中表现出色。@JFSebastian不幸的是,在我遇到这个问题的大背景下,这是行不通的。是的,我可以按照您的建议提取所有xml片段,但我还需要在注释之后解析源代码,而语法是必需的;逐行执行正则表达式搜索将在文件中添加一个额外的循环。@迈克:正则表达式只是一个如何提取注释行的示例。从更大的角度来看,您使用解析器来提取相关注释(比解析xml简单得多),如果您觉得有必要,它不会阻止您使用xml解析器来解析xml。@PaulMcGuire的解决方案也可以,但这正是我应该使用的(这是最简单的…)Thansk!
xmlComment = _cPoundOpenXmlComment + pp.SkipTo(_cPoundCloseXmlComment) + _cPoundCloseXmlComment 
import pyparsing as pp

text = '''\
///<summary>
/// foobar
///</summary>
blah blah
///<summary> /// bar ///</summary>
///<summary>  ///<summary> /// baz  ///</summary> ///</summary>    
'''

comment=pp.nestedExpr("///<summary>","///</summary>")
for match in comment.searchString(text):
    print(match)
    # [['///', 'foobar']]
    # [['///', 'bar']]
    # [[['///', 'baz']]]
import re
from xml.etree import cElementTree as etree

# extract all /// lines
lines = re.findall(r'^\s*///(.*)', text, re.MULTILINE)

# parse xml
root = etree.fromstring('<root>%s</root>' % ''.join(lines))
print root.findtext('summary')
# -> foobar