解析未知长度的Unicode名称

时间:2016-05-17 04:48:00

标签: python-3.x pyparsing

我一直在思考这个问题,我似乎无法找到解决方案。

我正在使用pyparsing来解析包含事件摘要的文本文件。每个文本文件包含许多事件。在几行标题信息之后,每个事件都会按以下格式列出多个人及其相关数据:

字整数:用户名(整数字字词)

  1. 是静态的,并且始终相同
  2. 整数是任何int
  3. 用户名可以是任何unicode字符,包括符号,也可以包含空格
  4. 我似乎无法构建可以处理所有这些可能性的语法。解析奇怪的unicode字符以及空格/符号时会遇到困难。下面的例子3让我感到难过。

    示例:

    你好1:-fred,123(100 hello stack overflow)

    你好2:我的名字是布伦特(250 hello stack overflow)

    你好3:äää+óóó(0 hello stack overflow)

    任何人都有任何提示吗?

    修改

    感谢您的回复。这就像魅力一样,但是当我转到文本文件的下一部分时,我又遇到了同样的问题。不确定我是应该开始一个新问题,还是仅仅添加到这个问题。

    我现在正在尝试解析以下类型的行:

    用户名:action-name action-details 用户名操作

    实施例

    brent morrow: add 10 to 20
    
    brent:morrow: walks
    
    äää + óóó: stands
    
    brent morrow has returned
    

    所有动作名称和动作细节都是静态的并且是已知的。

    所以我遇到了一个问题,我无法跳到用户名以外的文本,因为它可能是许多不同操作之一。它最终只打印整个文本文件(或至少是其中很大一部分)。

    我绝对难过。我基本上想找到一种展望未来的方法,找到以下内容:

    冒号+动作名称+动作细节

    空白+行动

    ...然后在此之前获取所有字符(用户名)。但是动作名称/动作细节/动作可以是预定义动作列表中的众多动作之一。负面的先行,〜,看起来很有希望,但我似乎无法找到接受用户名的所有unicode字符的解决方案。

    正在解析的文本文件来自我控制之外的第三方,因此无法找到更具体地构建源文件的方法。

1 个答案:

答案 0 :(得分:2)

尝试使用SkipTo(代码使用最新的pyparsing 2.1.4 runtests功能):

# -*- coding: utf-8 -*-

tests = """
    # a regular line
    hello 1: -fred,123 (100 hello stack overflow)

    # a username with spaces
    hello 2: my name is brent (250 hello stack overflow)

    # a username with non-ASCII
    hello 3: äää + óóó (0 hello stack overflow)
"""

from pyparsing import *

COLON,LPAR,RPAR = map(Suppress, ":()")
integer = pyparsing_common.integer

leading = "hello" + integer + COLON
trailing = LPAR + integer + "hello" + "stack" + "overflow" + RPAR

strip = lambda t: t[0].strip()
line = leading + SkipTo(trailing).setParseAction(strip) + trailing

line.runTests(tests)

给出:

# a regular line
hello 1: -fred,123 (100 hello stack overflow)
['hello', 1, '-fred,123', 100, 'hello', 'stack', 'overflow']

# a username with spaces
hello 2: my name is brent (250 hello stack overflow)
['hello', 2, 'my name is brent', 250, 'hello', 'stack', 'overflow']

# a username with non-ASCII
hello 3: äää + óóó (0 hello stack overflow)
['hello', 3, '\xe4\xe4\xe4 + \xf3\xf3\xf3', 0, 'hello', 'stack', 'overflow']

练习OP:将结果名称添加到整数和用户名,以便更轻松地访问已解析的字段。

相关问题