0

I want to split the string using the arithmetic and logical operators present in the string. Sample string looks like as below a,b,c are constant value and its value has to fetched from database and compute the expression and return True or False

Eg:

'a >= 10 AND b >=20 OR c<=100'

or

'a >=10 OR b < 100 AND c = 100'

I need to split this based on OR, AND,NOT or any logical operators as

a >= 10 
b >= 20
c <= 100

and compute the conditions with the operators(AND, OR ) given

Ex: a = 10 , b=25 , c=50

I need to evaluate like 10 >= 10 AND 25 >=20 OR 50 <=100 and return True

Is there any easy way to do this in python?

PGS
  • 1,046
  • 2
  • 17
  • 38
  • 1
    You could use [Pyparsing](http://pyparsing.wikispaces.com/) module and read this [post](https://stackoverflow.com/questions/2371436/evaluating-a-mathematical-expression-in-a-string). – mforpe Jul 30 '17 at 10:59
  • 1
    Possible duplicate of [Evaluating a mathematical expression in a string](https://stackoverflow.com/questions/2371436/evaluating-a-mathematical-expression-in-a-string) – mforpe Jul 30 '17 at 11:01

2 Answers2

3

You can use eval() to execute string statement. For e.g.

eval('a >= 10 and b >=20 or c<=100')

It will evaluate to True id a,b and c are already defined.

Note: logical operator used should be in lower case like and not AND

bobble bubble
  • 16,888
  • 3
  • 27
  • 46
Pritam Pan
  • 133
  • 7
1

this is a variant using sympy and a bit of regex.

this will do the following:

  1. surround the individual expressions a>=10 with brackets
  2. replace AND and OR with & and |
  3. sympify the string in order to get a valid sympy expression
  4. substitute whatever values you want for the variables

and here is the code for that:

from re import sub
from sympy import symbols, sympify

a, b, c = symbols('a b c')

strg = 'a >= 10 AND b >=20 OR c<=100'

def repl(match):
    '''
    surround match with quotes
    '''
    return '({})'.format(match.group())

strg1 = sub('([abc]\s*[<>=]+\s*\d*)', repl, strg)
print(strg1)  # (a >= 10) AND (b >=20) OR (c<=100)
strg2 = strg1.replace('AND', '&').replace('OR', '|')
print(strg2)  # (a >= 10) & (b >=20) | (c<=100)
sympy_expr = sympify(strg2)
print(sympy_expr)  # Or(And(a >= 10, b >= 20), c <= 100)

subs = {a: 10, b: 25, c: 50}
res = sympy_expr.subs(subs)
print(res)  # True
hiro protagonist
  • 44,693
  • 14
  • 86
  • 111
  • Thanks for the answer. Here in my example i mentioned as a,b,c ..but actual statement it can be anyting. I need to split and take it and fetch the value and evaluate . I won't be able to use as `a, b, c = symbols('a b c')' – PGS Jul 30 '17 at 16:58
  • sorry, i can only answer the question you post. but maybe there is something that can help you in the answer (e.g. the regex to get the comparison is there [may need small modifications if you have different variable names]). good luck! – hiro protagonist Jul 30 '17 at 17:06