1

我有用于字符串替换的自定义格式化程序,它应该仅与替换字段语法中的标准字符串格式化程序不同:而不是'{f}'.format(f=123)我想要'$(f)'.format(f=123)的(后者实际上将使用自定义格式化程序类,如shell_formatter.format(...))。

我覆盖了string.Formatter.parse使用新语法,但我最终使用的正则表达式并不能让我很满意。

问题:

  1. 我可以让正则表达式更简单/更具可读性吗?
  2. 有没有更简单的方法来更改我错过的格式语法?

更新

  1. 简化了正则表达式并添加了新的测试。
  2. 目的是从模板生成 C 源代码文件。由于 C 过度使用卷曲,因此在这里使用'{f}'语法显然行不通。
  3. string.Template模块不支持复杂的访问说明符(参见第三个测试)。

代码如下:

#! /usr/bin/env python3

import string
import re


class ShellFormatter(string.Formatter):
    def parse(self, format_string):
        for m in re.finditer(
            r"""(?: \$ \( ( [^)]+ ) \) )   # the field access specifier
              | (
                    (?:
                        \n | . (?= \$ \( ) # any one single character before the '$('
                    )
                  | (?:
                        \n | . (?! \$ \( ) # any one single character, except the one before the '$('
                    )*
                )""",
            format_string,
            re.VERBOSE):

            if m.group(1):
                yield ('', m.group(1), '', None)

            if m.group(2):
                yield (m.group(2), None, None, None)


def main():
    ...


def test():
    s = 'ashyudiqhw $(field) fwekojnwe'
    ss = 'checking helll kpoqjkf3483297 18934417 hnhfnqi^$&*@&2 1748912$&#^$\n467812\n^$ jfimopw279\nashyudiqhw $(field) fwekojnwe\njjhjhj$(notfield)'
    sss = 'const int complex_stuff = $(stuff[0][field1][field2]);'
    sf = ShellFormatter()
    assert sf.format(s, field='zzz') == 'ashyudiqhw zzz fwekojnwe'
    assert sf.format(ss, field='zzz', notfield='xxx') == 'checking helll kpoqjkf3483297 18934417 hnhfnqi^$&*@&2 1748912$&#^$\n467812\n^$ jfimopw279\nashyudiqhw zzz fwekojnwe\njjhjhjxxx'
    assert sf.format(sss, stuff=[ { 'field1': { 'field2': '0x1234' } } ]) == 'const int complex_stuff = 0x1234;'


if __name__ == '__main__':
    test()
    main()
4

0 回答 0