Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Python Regex to start from inner match

I am working on a regex in Python that is converting a mathematical expression to the power format in Sympy language pow(x,y). For example, it takes 2^3 and returns pow(2,3).

My current pattern is:

# pattern
pattern = re.compile(r'(.+?)\^(.*)')

To find the math for nested expressions, I use a for loop to count the number of ^(hat)s and then use re.sub to generate the power format:

# length of the for loop
num_hat = len(re.findall(r'\^', exp))

# for nested pow
for i in range(num_hat): 
   exp = re.sub(pattern, r'pow(\1,\2)', exp)
return exp

This method does not work for nested ^ expressions such as a^b^c^d or sin(x^2)^3 as the position of the final parenthesis is not correct.

For a^b^c^d it returns pow(pow(pow(a,b,c,d)))

For sin(x^2)^3 it returns pow(pow(sin(x,2),3))

Is there any way to overcome this issue? I tried the negative lookahead but it is still not working

like image 313
LoneWolf Avatar asked Jun 21 '26 23:06

LoneWolf


1 Answers

There is no nice way of saying this, but you have an extreme case of an XY problem. What you apparently want is to convert some mathematical expression to SymPy. Writing your own regular expression seems like a very tedious, error-prone, and possibly impossible approach to this.

Being a vast symbolic library, SymPy comes with an entire parsing submodule, which allows you to tweak the parsing expressions in all detail, in particular convert_xor governs what happens to the ^ character. However, it appears you do not need to do anything since converting ^ to exponentiation is the default. You can therefore simply do:

from sympy import sympify
print( sympy.sympify("a^b^c^d") )    # a**(b**(c**d))
print( sympy.sympify("sin(x^2)^3") ) # sin(x**2)**3

Note that ** is equivalent to pow, so I am not sure why you are insisting on the latter. If you need an output that shall work in yet another programming language, that’s what the printing module is for and it’s comparably easy to change this yourself. Another thing that may help you obtain the desired form is sympy.srepr.

like image 167
Wrzlprmft Avatar answered Jun 24 '26 12:06

Wrzlprmft