Enumerating formatting strings

Peter Otten __peter__ at web.de
Tue Apr 19 03:31:53 EDT 2005


Steve Holden wrote:

> I was messing about with formatting and realized that the right kind of
> object could quite easily tell me exactly what accesses are made to the
> mapping in a string % mapping operation. This is a fairly well-known
> technique, modified to tell me what keys would need to be present in any
> mapping used with the format.

...

> I've been wondering whether it's possible to perform a similar analysis
> on non-mapping-type format strings, so as to know how long a tuple to
> provide, or whether I'd be forced to lexical analysis of the form string.

PyString_Format() in stringobject.c determines the tuple length, then starts
the formatting process and finally checks whether all items were used -- so
no, it's not possible to feed it a tweaked (auto-growing) tuple like you
did with the dictionary.

Here's a brute-force equivalent to nameCount(), inspired by a post by Hans
Nowak (http://mail.python.org/pipermail/python-list/2004-July/230392.html).

def countArgs(format):
    args = (1,) * (format.count("%") - 2*format.count("%%"))
    while True:
        try:
            format % args
        except TypeError, e:
            args += (1,)
        else:
            return len(args)
            
samples = [
    ("", 0),
    ("%%", 0),
    ("%s", 1),
    ("%%%s", 1),
    ("%%%*.*d", 3),
    ("%%%%%*s", 2),
    ("%s %*s %*d %*f", 7)]
for f, n in samples:
    f % ((1,)*n) 
    assert countArgs(f) == n    

Not tested beyond what you see.

Peter




More information about the Python-list mailing list