python中eval()函数实际应用的一个疑问?

题目描述

获取一个随机验证码并通过eval()函数校对是否与用户输入值一致

题目来源及自己的思路

我的思路是直接eval函数进行计算字符串表达式,但不行,后来发现新建一个变量可以完成完整代码,如我注释掉的两行代码,但我不明白为什么我这种直接调用的不行?

相关代码

粘贴代码文本(请勿用截图)
import random

a = str(random.randint(0, 10))                    

b = str(random.randint(0, 10))

x = input(f"请输入计算验证信息的结果({a}+{b}):")

# y = f"{a} + {b}"

# r = eval(y)

r = str(eval('a + b'))

if x == str(r):

print("您已经通过验证!")

else:

print("您的验证信息输入有误!")

你期待的结果是什么?实际看到的错误信息又是什么?

我希望看到我验证成功
实际看到的截图如下
python中eval()函数实际应用的一个疑问?


回答:

eval('a + b') eval需要在上下文中查找,ab的值的。很显然,并没有在上下文中设置a, b的值。

eval(expression[, globals[, locals]])

- expression -- 表达式。

- globals -- 变量作用域,全局命名空间,如果被提供,则必须是一个字典对象。

- locals -- 变量作用域,局部命名空间,如果被提供,可以是任何映射对象。


所以,你这样写才可以

>>> a = 3

>>> b = 4

>>> eval('a+b', {'a': a, 'b': b})

7


关于globalslocals你可以在这里看下。

https://docs.python.org/3/lib...
https://docs.python.org/3/lib...
https://docs.python.org/3/lib...

eval('a+b', {'a': a, 'b': b}) 其实就是在 globals() 全局命名空间中添加了如下:

>>> globals()

{'__name__': '__main__', '__doc__': None, '__package__': None, '__loader__': <class '_frozen_importlib.BuiltinImporter'>, '__spec__': None, '__annotations__': {}, '__builtins__': <module 'builtins' (built-in)>, 'a': 3, 'b': 4}


回答:

其实问题是因为你的 ab 是字符串,导致你的 eval('a + b') 其实是对于两个字符串先进行了字符串的拼接( eval('"a" + "b"') = eval('ab') = ab ),才再次执行了 eval 的计算。所以你始终得到的结果是a和b字符串的拼接,而不是数字的相加。

也就是说:

import random

a = str(random.randint(0, 10)) # a是一个字符串

b = str(random.randint(0, 10)) # b是一个字符串

x = input(f"请输入计算验证信息的结果({a}+{b}):")

r = str(eval('a + b')) # 其实等价于 eval('str(a) + str(b)') => eval('"a" + "b"') => eval('ab')

# print(r):假设a是'5',b是'6',那么r是'56' <=> eval('"5" + "6"')

if x == str(r):

print("您已经通过验证!")

else:

print("您的验证信息输入有误!")

所以如果你把 ab 前面的str这个给去掉,a和b就是整型变量,然后你的写法就是对的了。

改进如下:

# 写法一:

import random

a = random.randint(0, 10) # 去掉这里的str,不需要转换为string类型

b = random.randint(0, 10) # 去掉这里的str,不需要转换为string类型

x = input(f"请输入计算验证信息的结果({a}+{b}):")

r = str(eval('a + b'))

if x == str(r):

print("您已经通过验证!")

else:

print("您的验证信息输入有误!")

# 写法二:

import random

a = str(random.randint(0, 10))

b = str(random.randint(0, 10))

x = input(f"请输入计算验证信息的结果({a}+{b}):")

r = str(eval(f"{a} + {b}")) # 将这里的表达式改成f"{a} + {b}", 这样eval里面就是纯粹的 a + b, 而不是"a" + "b".

if x == str(r):

print("您已经通过验证!")

else:

print("您的验证信息输入有误!")

以上是 python中eval()函数实际应用的一个疑问? 的全部内容, 来源链接: utcz.com/p/938639.html

回到顶部