compiler module supports 'statements as expressions'

Tom Locke tom at livelogix.com
Tue May 4 04:56:51 EDT 2004


Hi,

I am writing a compiler (in python) that targets python byte-code,
using compiler.ast and compiler.pycodegen.

The language is lisp-like in that there is no statement / expression
separation.

e.g. I can do (in a python-like syntax)

    print (if x: "yes" else: "no")

or

while line = raw_input("> "); line != "":
    print line

Having hacked away for a short while on a translator to make these
things into separate statements that would be legal in Python, I was
VERY surprised when I accidentally discovered that this seems to be
LEGAL at the byte-code level. (CPython 2.3.3, Win XP)

compiler.pycodegen.ModuleCodeGenerator generates working code for AST
fragments like these:

Printnl([If([(Name('x'), Stmt([Const('yes')]))],
            Stmt([Const('no')]))],
        None)

and

While(Stmt([Assign([AssName('line', 'OP_ASSIGN')],
                   CallFunc(Name('raw_input'), [Const('> ')],
                            None, None)),
            Compare(Name('line'), [('!=', Const(''))])]),
      Stmt([Printnl([Name('line')], None)]), None)]))

AST 'statement' nodes, when used in an expression context, evaluate as
follows.

If: value of the executed clause

Stmt: value of the last statement in the list

While and Assign: Undefined – python crashes if you try to do
something with these values.

This is really very helpful for me – it's just the semantics I wanted!

I think I'm right in saying that there's no legal Python that parses
into ASTs like these, right?

Can I rely on this?? Is it there for a reason? (e.g. to support
certain optimizations?) Is this just serendipity – the 'natural'
behavior of the stack based byte-code interpreter?

Thanks,

Tom.



More information about the Python-list mailing list