资源:
[This] is some text with [some [blocks that are nested [in a [variety] of ways]]]
结果文字:
[This] is some text with
从查看threads at stack overflow,我认为你不能为此做正则表达式.
有没有一种简单的方法来做到这一点 – >或者必须达到pyparsing(或其他解析库)?
解决方法:
将OP的示例作为规范(必须删除包含更多嵌套块的任何块),那么……:
import itertools
x = '''[This] is some text with [some [blocks that are nested [in a [variety]
of ways]]] and some [which are not], and [any [with nesting] must go] away.'''
def nonest(txt):
pieces = []
d = 0
level = []
for c in txt:
if c == '[': d += 1
level.append(d)
if c == ']': d -= 1
for k, g in itertools.groupby(zip(txt, level), lambda x: x[1]>0):
block = list(g)
if max(d for c, d in block) > 1: continue
pieces.append(''.join(c for c, d in block))
print ''.join(pieces)
nonest(x)
这会发出
[This] is some text with and some [which are not], and away.
在正常时间假设下似乎是理想的结果.
我们的想法是在级别上计算一个并行的计数列表“我们此时如何嵌套”(即,到目前为止我们遇到了多少打开和尚未关闭的括号);然后将具有groupby的文本的zip级别划分为具有零嵌套和嵌套的备用块> 0.对于每个块,然后计算此处的最大嵌套(对于具有零嵌套的块将保持为零 – 更一般地,它仅是整个块中嵌套级别的最大值),并且如果得到的嵌套是< = 1 ,保留相应的文本块.请注意,我们需要将组g组成一个列表块,因为我们要执行两次迭代传递(一次用于获取最大嵌套,一次用于将字符重新连接到一个文本块中) - 要在一次传递中完成需要在嵌套循环中保留一些辅助状态,这在这种情况下不太方便.