其他分享
首页 > 其他分享> > Pyparsing:嵌套的Markdown强调

Pyparsing:嵌套的Markdown强调

作者:互联网

我正在闲逛着一些简单的Markdown文本,可以一起学习和学习Pyparsing和语法.我几乎无法解决就遇到了一个问题.我正在尝试解析CommonMark规范的简单版本以进行强调.在此设置中,允许嵌套强调,因此

*foo *bar* baz*

应该给:

<em>foo <em>bar</em> baz</em>

我尝试使用递归定义来匹配它,但是它不起作用.这是一些示例代码:

from pyparsing import *

text = Word(printables,excludeChars="*")
enclosed = Forward()
emphasis = QuotedString("*").setParseAction(lambda x: "<em>%s</em>" % x[0],contents=enclosed)
enclosed << emphasis | text

test = """
*foo *bar* bar*
"""

print emphasis.transformString(test)

但是我从中得到的是:

<em>foo </em>bar<em> bar</em>

原谅我的笨拙;有人可以指出我正确的方向吗?

编辑:

针对abarnert的一个重大问题,我将进行澄清.我只是在玩耍,所以我可以使用任意限制的表示形式.我假设只出现一个’*,并且它们不会相邻出现.这就使空白变得毫无歧义:*不紧跟空格就打开重点,并且*不紧跟空格就将其关闭.

即使这样,我也不知道如何进行Pyparsing.某种基于堆栈的方法,推动开*并在验证为关闭时弹出它们? Pyparsing怎么办?还是有更有效的方法?

解决方法:

有了这些附加规则,我认为您根本不必担心递归,只要找到它们的开头和结尾强调表达式即可,无论它们是否匹配:

from pyparsing import *

openEmphasis = (LineStart() | White()) + Suppress('*')
openEmphasis.setParseAction(lambda x: ''.join(x.asList()+['<em>']))
closeEmphasis = '*' + FollowedBy(White() | LineEnd())
closeEmphasis.setParseAction(lambda x: '</em>')

emphasis = (openEmphasis | closeEmphasis).leaveWhitespace()

test = """
*foo *bar* bar*
"""
print test
print emphasis.transformString(test)

印刷品:

*foo *bar* bar*

<em>foo <em>bar</em> bar</em>

您不是第一个使用此类应用程序的人.当我在PyCon’06上发表演讲时,一个急切的与会者赶紧跳出来解析一些降价促销,输入字符串类似“ **** a ** b **** c **”之类.我们在一起进行了一些工作,但是消歧规则对于基本的pyparsing解析器来说太了解上下文了.

标签:pyparsing,python
来源: https://codeday.me/bug/20191029/1957887.html