Override 'and' and 'or'

John Machin sjmachin at lexicon.net
Sun Oct 7 17:21:50 EDT 2007


On 8/10/2007 1:57 AM, Diez B. Roggisch wrote:
> Kay Schluehr schrieb:

>> You can see what "and" and "or" are actually doing:
>>
>> import dis
>> dis.dis(lambda: x or y and z)
>>
>>   1           0 LOAD_GLOBAL              0 (x)
>>               3 JUMP_IF_TRUE            11 (to 17)
>>               6 POP_TOP
>>               7 LOAD_GLOBAL              1 (y)
>>              10 JUMP_IF_FALSE            4 (to 17)
>>              13 POP_TOP
>>              14 LOAD_GLOBAL              2 (z)
>>         >>   17 RETURN_VALUE
>>
>> Here you can see nicely that they are not implemented as specialized
>> opcodes but being compiled to jumps. This causes their lazy nature. If
> 
> Very cool, didn't know that.
> 

<rant>

Not very cool at all IMHO, because:
1. There's no other way to avoid unnecessarily evaluating the second 
operand besides using jumps.
2. POP_TOP [used even in normal test & jump situations] is horrible, and 
there are long-known better ways of doing it:

E.g. "Recursive Descent Compiling", by A.J.T. Davie and R. Morrison 
[pub: Ellis Horwood, Chichester, 1981] says on page 146: "... jumptt 
branches if the top stack element is true and merely removes it 
otherwise. A similar sequence can be used for 'and' but with jumpff 
replacing jumptt."

C Python uses two JUMP_IF_bool[_NEVER_POP] instructions, followed in 
most cases by POP_TOP.

E.g.
 >>> dis.dis(lambda: tval if arg else fval)
   1           0 LOAD_GLOBAL              0 (arg)
               3 JUMP_IF_FALSE            7 (to 13)
               6 POP_TOP
               7 LOAD_GLOBAL              1 (tval)
              10 JUMP_FORWARD             4 (to 17)
         >>   13 POP_TOP
              14 LOAD_GLOBAL              2 (fval)
         >>   17 RETURN_VALUE
 >>>

IMHO 4 more jump instructions
     2 x JUMP_IF_bool_ALWAYS_POP (simple cases)
and 2 x JUMP_IF_bool_ELSE_POP (and/or)
would be very useful.

</rant>



More information about the Python-list mailing list