Комментарии 15
Унарный минус эо признак числа, а не оператор. Такие вещи должны быть выявлены на этапе разбиения на лексемы исходного выражения
Короче нужен рекурсивный спуск или взрослые табличные парсеры
А как насчет "-(2 + 3 — 4*5)" или в общем виде "-(a + b — c*d)" и ему подобных?Все парсится и вычисляется правильно



Язык древний, но работает
Можно использовать 0 - (2 + 3 - 4*5) в инфиксной записи. В постфиксной записи:
0 2 3 + 4 5 * - -
Легко: если встретился минус, а перед ним не было операндов (т.е. начало выражения или перед этим была скобка) то пушим ноль в качестве операнда.
Альтернатива: заводим (внутреннюю) операцию «унарный минус» с соответствующим приоритетом (выше умножения), и пушим её, если не было операнда и был минус.
Конечно, тут приходится новую яйчейку памяти заводить под «не было операндов». А всё потому, что один знак «минус» использован для разных операций. Логически они одинаковые, но имеют разное число аргументов.
С унарными операциями, имеющими свой собственный знак, такой проблемы нет. Правда, нас спасает то, что математические унарные операции - префиксные и имеют высокий приоритет. Благодаря этим свойствам, они вписываются в алгоритм.
Учитывайте, что при нормализации вашего выражения, мы получаем -1 * (a + b - c*d), где - становится признаком числа.
Я, кстати, делал программу для вычисления математических выражений. Если в начале выражения встречается знак минуса, то в ответ записывается 0, а минус кладется в стэк, т.е. происходит преобразование унарного минуса в бинарный.
А также в математических выражениях ещё есть степени и функции.
степени и функции (одной переменной) - это унарные операторы. думаю, в такой записи бинарные и унарные операторы надо четко различать. Вот что делать с унарным минусом, чтобы его н путать с бинарным? лучше наверное переименовать, чтобы "-" был только бинарным (ну или отказаться от унарного минуса вовсе, заменив его на "0 -" )
степень это оператор выше умножения.
а функции надо выделять на этапе разбора лексем первоначального выражения и выписывать их как унарный оператор на самом высоком уровне. Т.е. у нас есть выражение:
exp(1+x)*-2
Его надо распарсить на 2 массива
f1 = exp . [1, +, x]
[f1, *, -2]
далее преобразуем оба массива в обратную польскую
f1 = exp . [1, x, +] = 1 x + exp
f1 -2 *
И во втором выражении подменяем f1
1 x + exp -2 *
Алгоритм сортировочной станции жеж. Все кристально ясно
Почему работает алгоритм преобразования инфиксной записи в постфиксную