Eval Python ()

O método eval () analisa a expressão passada para este método e executa a expressão python (código) dentro do programa.

Em termos simples, a eval()função executa o código Python (que é passado como um argumento) dentro do programa.

A sintaxe de eval()é:

 eval (expressão, globais = Nenhum, locais = Nenhum)

Parâmetros eval ()

A eval()função leva três parâmetros:

  • expressão - a string analisada e avaliada como uma expressão Python
  • globais (opcional) - um dicionário
  • locais (opcional) - um objeto de mapeamento. Dicionário é o tipo de mapeamento padrão e comumente usado em Python.

O uso de globais e locais será discutido posteriormente neste artigo.

Valor de retorno de eval ()

O método eval () retorna o resultado avaliado da expressão.

Exemplo 1: como eval () funciona em Python

 x = 1 print(eval('x + 1'))

Resultado

 2

Aqui, a eval()função avalia a expressão x + 1e printé usada para exibir esse valor.

Exemplo 2: Exemplo prático para demonstrar o uso de eval ()

 # Perimeter of Square def calculatePerimeter(l): return 4*l # Area of Square def calculateArea(l): return l*l expression = input("Type a function: ") for l in range(1, 5): if (expression == 'calculatePerimeter(l)'): print("If length is ", l, ", Perimeter = ", eval(expression)) elif (expression == 'calculateArea(l)'): print("If length is ", l, ", Area = ", eval(expression)) else: print('Wrong Function') break

Resultado

 Digite uma função: calculArea (l) Se o comprimento for 1, Área = 1 Se o comprimento for 2, Área = 4 Se o comprimento for 3, Área = 9 Se o comprimento for 4, Área = 16

Avisos ao usar eval ()

Considere uma situação em que você está usando um sistema Unix (macOS, Linux etc) e importou o osmódulo. O módulo os fornece uma maneira portátil de usar as funcionalidades do sistema operacional, como ler ou gravar em um arquivo.

Se você permitir que os usuários insiram um valor usando eval(input()), o usuário pode emitir comandos para o arquivo de mudança ou até mesmo apagar todos os arquivos usando o comando: os.system('rm -rf *').

Se você estiver usando eval(input())em seu código, é uma boa ideia verificar quais variáveis ​​e métodos o usuário pode usar. Você pode ver quais variáveis ​​e métodos estão disponíveis usando o método dir ().

 from math import * print(eval('dir()'))

Resultado

('__annotations__', '__builtins__', '__cached__', '__doc__', '__file__', '__loader__', '__name__', '__package__', '__spec__', 'acos', 'acosh', 'asin', ' asinh ',' atan ',' atan2 ',' atanh ',' ceil ',' comb ',' copysign ',' cos ',' cosh ',' degrees ',' dist ',' e ',' erf ' , 'erfc', 'exp', 'expm1', 'fabs', 'fatorial', 'floor', 'fmod', 'frexp', 'fsum', 'gamma', 'gcd', 'hypot', ' inf ',' isclose ',' isfinite ',' isinf ',' isnan ',' isqrt ',' ldexp ',' lgamma ',' log ',' log10 ',' log1p ','log2 ',' modf ',' nan ',' os ',' perm ',' pi ',' pow ',' prod ',' radianos ',' resto ',' sin ',' sinh ',' sqrt ' , 'tan', 'tanh', 'tau', 'trunc')

Restringindo o uso de métodos e variáveis ​​disponíveis em eval ()

Na maioria das vezes, todos os métodos e variáveis ​​disponíveis usados ​​na expressão (primeiro parâmetro para eval()) podem não ser necessários ou mesmo ter uma falha de segurança. Pode ser necessário restringir o uso desses métodos e variáveis ​​para eval(). Você pode fazer isso passando parâmetros opcionais globais e locais (dicionários) para a eval()função.

1. Quando os parâmetros globais e locais são omitidos

Se ambos os parâmetros forem omitidos (como em nossos exemplos anteriores), a expressão é executada no escopo atual. Você pode verificar as variáveis ​​e métodos disponíveis usando o seguinte código:

 print(eval('dir()')

2. Passando parâmetro global; parâmetro locals é omitido

Os parâmetros globais e locais (dicionários) são usados ​​para variáveis ​​globais e locais, respectivamente. Se o dicionário local for omitido, o padrão será o dicionário global. Ou seja, os globais serão usados ​​para variáveis ​​globais e locais.

Observação: você pode verificar o dicionário global e local atual em Python usando os métodos integrados globals () e locals (), respectivamente.

Exemplo 3: Passando dicionário vazio como parâmetro global

 from math import * print(eval('dir()', ())) # The code will raise an exception print(eval('sqrt(25)', ()))

Resultado

 ('__builtins__') Traceback (última chamada mais recente): Arquivo "", linha 5, em impressão (eval ('sqrt (25)', ())) Arquivo "", linha 1, em NameError: nome 'sqrt' não está definido

Se você passar um dicionário vazio como globais, apenas os __builtins__estarão disponíveis para expression(primeiro parâmetro para o eval()).

Embora tenhamos importado o mathmódulo no programa acima, a expressão não pode acessar nenhuma função fornecida pelo módulo matemático.

Exemplo 4: Disponibilizando Certos Métodos

 from math import * print(eval('dir()', ('sqrt': sqrt, 'pow': pow)))

Resultado

 ('__builtins__', 'pow', 'sqrt')

Aqui, a expressão só pode usar sqrt()os pow()métodos e junto com __builtins__.

Também é possível alterar o nome do método disponível para a expressão de acordo com sua vontade:

 from math import * names = ('square_root': sqrt, 'power': pow) print(eval('dir()', names)) # Using square_root in Expression print(eval('square_root(9)', names))

Resultado

 ('__builtins__', 'poder', 'raiz quadrada') 3,0

No programa acima, square_root()calcula a raiz quadrada usando sqrt(). No entanto, tentar usar sqrt()diretamente gerará um erro.

Exemplo 5: Restringindo o uso de built-ins

Você pode restringir o uso de __builtins__na expressão da seguinte maneira:

 eval(expression, ('__builtins__': None))

3. Transmitindo dicionários globais e locais

Você pode disponibilizar funções e variáveis ​​necessárias para uso, passando o dicionário de locais. Por exemplo:

 from math import * a = 169 print(eval('sqrt(a)', ('__builtins__': None), ('a': a, 'sqrt': sqrt)))

Resultado

 13,0

Neste programa, a expressão pode ter apenas o sqrt()método e a variável a. Todos os outros métodos e variáveis ​​estão indisponíveis.

Restringir o uso de eval(), passando dicionários globais e locais, tornará seu código seguro, especialmente quando você estiver usando a entrada fornecida pelo usuário para o eval()método.

Nota: Às vezes, eval()não é seguro, mesmo com nomes limitados. Quando um objeto e seus métodos se tornam acessíveis, quase tudo pode ser feito. A única maneira segura é validando a entrada do usuário.

Artigos interessantes...