我目前教大学一年级学生python,我很惊讶地发现,我的一些学生决定使用(并且被奇怪的行为混淆)看似无害的input
函数,正在隐藏在它背后调用eval
。
所以我的问题是,为什么input
函数调用eval
,以及这对于raw_input
更安全不会更有用?据我所知,这在Python 3中有所改变,但它首先似乎是一个不寻常的设计决定。
答案 0 :(得分:38)
在raw_input上使用Python 2的输入是否有用?
否强>
input()
评估用户提供的代码。它将Python的全部功能掌握在用户手中。使用生成器表达式/列表推导,__import__
和if/else
运算符,可以使用单个表达式实现Python所能做的任何事情。恶意用户可以使用input()
删除文件(__import__('os').remove('precious_file')
),对程序的其余部分进行monkeypatch(setattr(__import__('__main__'), 'function', lambda:42)
),......任何事情。
普通用户无需使用所有高级功能。如果您不需要表达式,请使用ast.literal_eval(raw_input())
- literal_eval
函数是安全的。
如果您是为高级用户撰写文章,请为他们提供更好的输入代码的方式。插件,用户模块等 - 具有完整Python语法的东西,而不仅仅是功能。
如果您完全确定自己知道自己在做什么,请说eval(raw_input())
。 eval
尖叫“我很危险!”受过训练的眼睛。但是,你很可能不会需要这个。
input()
是Python 3正在解决的旧设计错误之一。
答案 1 :(得分:7)
Python输入函数返回一个结果对象 评估表达式。 raw_input函数返回一个字符串
name = "Arthur"
age = 45
first = raw_input("Please enter your age ")
second = input("Please enter your age again ")
# first will always contain a string
# second could contain any object and you can even
# type in a calculation and use "name" and "age" as
# you enter it at run time ...
print "You said you are",first
print "Then you said you are",second
正在运行的示例:
示例:1
Prompt$ python yraw
Please enter your age 45
Please enter your age again 45
You said you are 45 Then you said you are 45
示例:2
Prompt$ python yraw
Please enter your age 45 + 7
Please enter your age again 45 + 7
You said you are 45 + 7 Then you said you are 52
Prompt$
Q值。为什么输入函数调用eval?
一个。考虑用户在输入中输入表达式'45 + 7'的情况,与python 2.x中的raw_input相比,输入将给出正确的结果
答案 2 :(得分:4)
input
几乎只用作交互式python shell的构建块。你肯定是正确的,它的工作方式令人惊讶,并且它的内容非常专用于内置 - 我认为它是从Python 3中删除的原因。
答案 3 :(得分:2)
raw_input
更好,它总是返回用户的输入而不做任何更改。
相反,input()
函数会尝试将您输入的内容转换为Python代码,并且存在安全问题,因此您应该避免使用它。
在实际程序中,不要使用input()
,使用处理您期望的特定输入格式的内容解析输入,而不是将输入评估为Python代码。