何时使用 ast.literal_eval [英] When to use ast.literal_eval

查看:72
本文介绍了何时使用 ast.literal_eval的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我遇到了这段代码并且它有效,但我不完全确定何时使用 ast 以及是否存在性能问题 使用它而不是获取input() 中的字符串值并将其转换为 int.

I came across this code and it works, but I am not entirely sure about when to use ast and whether there are performance issues when this is used instead of getting the string value from input() and converting it to int.

import ast

cyper_key = ast.literal_eval(input("Enter the key (a value between 0 and 25) : "))

# this get the user input as an int to the variable cyper_key

我阅读了我了解它的作用的文档.

I read the docs I understand what it does.

这可用于安全地评估包含 Python 的字符串来自不受信任来源的值,无需解析值自己.它不能评估任意复杂的表达式,例如涉及运算符或索引.

This can be used for safely evaluating strings containing Python values from untrusted sources without the need to parse the values oneself. It is not capable of evaluating arbitrarily complex expressions, for example involving operators or indexing.

我正在寻找对上述粗体点的解释.

I am looking for an explanation on above bold points.

推荐答案

何时使用.

ast.literal_eval(input()) 如果您希望用户提供一个列表(或类似的东西),将会很有用.例如 '[1,2]' 将被转换为 [1,2].

ast.literal_eval(input()) would be useful if you expected a list (or something similar) by the user. For example '[1,2]' would be converted to [1,2].

如果用户应该提供一个数字 ast.literal_eval(input()) 可以替换为 float(input())int(input()) 如果需要一个整数.

If the user is supposed to provide a number ast.literal_eval(input()) can be replaced with float(input()), or int(input()) if an integer is expected.

性能

请注意,过早的[微]优化是万恶之源.但既然您问:

要测试 ast.literal_eval(input())float(input() 的速度,您可以使用 timeit.

To test the speed of ast.literal_eval(input()) and float(input() you can use timeit.

时间将根据用户提供的输入而变化.

整数和浮点数是有效的输入,而其他任何东西都是无效的.输入 50% 整数、40% 浮点数和 10% 随机数作为输入,float(input()) 速度 x12.

Ints and floats are valid input, while anything else would be invalid. Giving 50% ints, 40% floats and 10% random as input, float(input()) is x12 faster.

使用 10%、10%、80% 和 float(input()) 速度 x6.

With 10%, 10%, 80% and float(input()) is x6 faster.

import timeit as tt

lst_size = 10**5

# Set the percentages of input tried by user.
percentages = {'ints': .10,
               'floats': .10,
               'strings': .80}
assert 1 - sum(percentages.values()) < 0.00000001

ints_floats_strings = {k: int(v*lst_size) for k, v in percentages.items()}

setup = """
import ast

def f(x):
    try:
        float(x)
    except:
        pass

def g(x):
    try:
        ast.literal_eval(x)
    except:
        pass

l = [str(i) for i in range({ints})]
l += [str(float(i)) for i in range({floats})]
l += [']9' for _ in range({strings}//2)] + ['a' for _ in range({strings}//2)]
""".format(**ints_floats_strings)

stmt1 = """
for i in l:
    f(i)
"""

stmt2 = """
for i in l:
    g(i)
"""


reps = 10**1
t1 = tt.timeit(stmt1, setup, number=reps)
t2 = tt.timeit(stmt2, setup, number=reps)

print(t1)
print(t2)

print(t2/t1)

这篇关于何时使用 ast.literal_eval的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

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