Dictionary string parser

Fredrik Lundh fredrik at pythonware.com
Tue Nov 22 17:26:30 CET 2005


Sebastjan Trepca wrote:

> is there any library or some way to parse dictionary string with list,
> string and int objects into a real Python dictionary?
>
> For example:
>
> >>> my_dict = dict_parser("{'test':'123','hehe':['hooray',1]}")
>
> I could use eval() but it's not very fast nor secure.

it's definitely slower than eval (which is written in C, after all), but it's
definitely more limited, and hopefully also more secure:

import cStringIO
import tokenize

def _parse(token, src):
    if token[1] == "{":
        out = {}
        token = src.next()
        while token[1] != "}":
            key = _parse(token, src)
            token = src.next()
            if token[1] != ":":
                raise SyntaxError("malformed dictionary")
            value = _parse(src.next(), src)
            out[key] = value
            token = src.next()
            if token[1] == ",":
                token = src.next()
        return out
    elif token[1] == "[":
        out = []
        token = src.next()
        while token[1] != "]":
            out.append(_parse(token, src))
            token = src.next()
            if token[1] == ",":
                token = src.next()
        return out
    elif token[0] == tokenize.STRING:
        return token[1][1:-1].decode("string-escape")
    elif token[0] == tokenize.NUMBER:
        try:
            return int(token[1], 0)
        except ValueError:
            return float(token[1])
    else:
        raise SyntaxError("malformed expression")

def myeval(source):
    src = cStringIO.StringIO(source).readline
    src = tokenize.generate_tokens(src)
    return _parse(src.next(), src)

print myeval("{'test':'123','hehe':['hooray',0x10]}")
{'test': '123', 'hehe': ['hooray', 16]}

hope this helps!

</F>






More information about the Python-list mailing list