I want my code to understand a string as a math expression, then output me this string with proper whitespaces.
- At first, I created my variables.
operators = ("+", "-", "*", "/", "%", "**", "//") # Math operators the code is going to identify in the string
oper = "20 *25" # The operation string before being formatted ('oper' stands for 'operation')
new_oper = "" # This is going to be the new operation string (desired output)
it = iter(oper.replace(" ", "")) # Removed all whitespaces from the operation string and made it an iterable
- I used the
next()method once, just so he could understand this method (inside my loop) as the character that comes right after the character the loop is in.
next(it)
- Then I started my loop to check every single character in the
operation string(already with no whitespaces).
for x in oper.replace(" ", ""):
try: # This try checks if I'm able to use the next() method. If I'm not, x is the last character in the string.
if x not in operators: # x is a number
if next(it) in operators:
new_oper += f"{x} " # If an operator comes right after a number, this number is printed with a whitespace, so they don't stay next to each other.
else:
new_oper += x
elif x in operators: # x is an operator
if x == "*":
if next(it) == "*":
new_oper += x # If another '*' comes after this '*', then it's a ** operator, so no whitespaces inserted (otherwise, they would be separated)
else:
new_oper += f"{x} "
elif x == "/":
if next(it) == "/":
new_oper += x # Same here: if there are 2 '/' next to each other, it's another operator ('//'), so no whitespaces inserted
else:
new_oper += f"{x} "
else:
new_oper += f"{x} "
except RuntimeError:
new_oper += x # x is the last character in the string, no needs to be formatted (it can't be an operator)
- Finally, after formatting everything, I wanted him to print the new string (
new_oper).
print(new_oper)
Check out these outputs (different values for oper):
When
oper = "20 *2"
Output
Traceback (most recent call last):
File "filename", line 12, in <module>
if next(it) in operators:
^^^^^^^^
StopIteration
# Desired output: 20 * 2
When
oper = "20 +2"
Output
20 + 2 # Correct output (just changed the operator comparing to the last one)
When
oper = "10+ 3 *2"
Output
10 + 3*2
# Desired output: 10 + 3 * 2
I'd appreciate any approach for my problem. I'm not a python expert (far away from that), so I also would appreciate any suggestions or even fixes in my code that may not directly help my problem.
Firstly, you need to change the
except RuntimeError:toexcept StopIteration:so that it is able to catch theStopIterationexception that is thrown by thenext()when it reaches the end of the string.You need to change the
elseto make it like this:Here, the
next(it)is so that the iterator is always in line with the value ofx. You callnext(it)once on all other path of theifexcept this one.With these 2 changes, it works on the examples given.
Suggestion:
It might be easier to iterate over the string using
enumeratelike this:instead of trying to keep the iterator and the loop in sync. This way, you can refer to the next character as
oper2[index+1](indexis the index of the current character) and for the current character, you can usex.For example, instead of
next(it), you would writeoper2[index+1]. This has the added benefit of being able to look further ahead (but you would need to doexcept IndexError:instead ofexcept StopIteration:)