[Tutor] eval use (directly by interpreter vs with in a script)

Danny Yoo dyoo at hashcollision.org
Mon Nov 3 19:48:01 CET 2014


On Mon Nov 03 2014 at 10:04:41 AM Alan Gauld <alan.gauld at btinternet.com>
wrote:

> On 03/11/14 17:33, Albert-Jan Roskam wrote:
>
> > I sometimes do something like
> > ifelse = "'teddybear' if bmi > 30 else 'skinny'"
> > weightcats = [eval(ifelse) for bmi in bmis]
> >
> > Would this also be a *bad* use of eval? It can be avoided, but this is
> so concise.
>
>
Yes, this is bad and you need to learn to instinctively wince when you see
this.  I know that I am.  :P

Even if you don't think about the security perspective, this is not good
from an engineering perspective: eval() is a dynamic recompilation of that
bit of source code every single time it goes through the loop.

The only thing that is "varying" here is bmi, and when we're writing a code
that's parameterized by a varying value, the tool to use isn't eval(): you
want to use a function.

Here's what this looks like:

#########################################
def ifelse(bmi): return 'teddybear' if bmi > 30 else 'skinny'
weightcats = [ifelse(bmi) for bmi in bmis]
#########################################

This is formatted deliberately to show that this is about the same length
as the original code, but significantly safer and more performant.
Performant because Python isn't reparsing the code that computes the bmi
label.

Safer because the behavior of the function-using code is much more
statically definable: you can tell from just reading the source code that
it can only do a few things: it either computes a value, or maybe it errors
if bmi is not a number.  eval(), on the other hand, can be a big black hole
of badness just waiting to happen.

Consider if 'bmi' were ever controlled from the outside world.  At the very
worst, the normal function approach will raise a runtime error, but that's
it.  In contrast, the eval approach can take over your machine.
-------------- next part --------------
An HTML attachment was scrubbed...
URL: <http://mail.python.org/pipermail/tutor/attachments/20141103/b2be7246/attachment.html>


More information about the Tutor mailing list