安全地评估简单的字符串方程式 [英] Safely evaluate simple string equation

查看:132
本文介绍了安全地评估简单的字符串方程式的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我正在编写一个程序,其中将方程式作为字符串输入,然后求值.到目前为止,我已经提出了以下建议:

I'm writing a program in which an equation is inputted as a string, then evaluated. So far, I've come up with this:

test_24_string = str(input("Enter your answer: "))
test_24 = eval(test_24_string)

我既需要此方程式的字符串版本,也需要评估的版本.但是,eval是非常危险的功能.但是,使用int()不起作用,因为它是一个方程式.是否有Python函数可以根据字符串来评估数学表达式,就像输入数字一样?

I need both a string version of this equation and an evaluated version. However, eval is a very dangerous function. Using int() doesn't work, though, because it's an equation. Is there a Python function that will evaluate a mathematical expression from a string, as if inputting a number?

推荐答案

一种方法是使用.它主要是用于优化(和多线程)的模块.操作,但它也可以处理数学python表达式:

One way would be to use numexpr. It's mostly a module for optimizing (and multithreading) numpy operations but it can also handle mathematical python expressions:

>>> import numexpr
>>> numexpr.evaluate('2 + 4.1 * 3')
array(14.299999999999999)

您可以对结果调用.item以获得类似python的类型:

You can call .item on the result to get a python-like type:

>>> numexpr.evaluate('17 / 3').item()
5.666666666666667

这是一个第三方扩展模块,因此在这里可能是完全过时的了,但是它绝对比eval更安全,并且支持许多功能(包括numpymath操作).如果还支持变量替换":

It's a 3rd party extension module so it may be total overkill here but it's definetly safer than eval and supports quite a number of functions (including numpy and math operations). If also supports "variable substitution":

>>> b = 10
>>> numexpr.evaluate('exp(17) / b').item()
2415495.27535753


使用python标准库的一种方法,尽管非常有限,但 ast.literal_eval .它适用于Python中最基本的数据类型和文字:


One way with the python standard library, although very limited is ast.literal_eval. It works for the most basic data types and literals in Python:

>>> import ast
>>> ast.literal_eval('1+2')
3

但是失败的原因是更复杂的表达式,例如:

But fails with more complicated expressions like:

>>> ast.literal_eval('import os')
SyntaxError: invalid syntax

>>> ast.literal_eval('exec(1+2)')
ValueError: malformed node or string: <_ast.Call object at 0x0000023BDEADB400>

不幸的是,除了+-之外,任何其他运算符都是不可能的:

Unfortunatly any operator besides + and - isn't possible:

>>> ast.literal_eval('1.2 * 2.3')
ValueError: malformed node or string: <_ast.BinOp object at 0x0000023BDEF24B70>

我在此处复制了部分文档,其中包含受支持的类型:

I copied part of the documentation here that contains the supported types:

安全地评估表达式节点或包含Python文字或容器显示的字符串.提供的字符串或节点只能由以下Python文字结构组成:字符串,字节,数字,元组,列表,字典,集合,布尔值和无.

Safely evaluate an expression node or a string containing a Python literal or container display. The string or node provided may only consist of the following Python literal structures: strings, bytes, numbers, tuples, lists, dicts, sets, booleans, and None.

这篇关于安全地评估简单的字符串方程式的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆