handling unary minus for shunting-yard algorithm - algorithm

Is there a better way to handle unary "-" in converting a infix expression to a postfix one?
The obvious one would be prefix every unary "-" with a 0. Does anyone know better implementation? Thanks!

The way I did this years ago was invent a new operator for my postfix expression. So when I encountered a unary minus in the infix, I'd convert it to #. So my postfix for a + -b became ab#+.
And, of course, my evaluator had to know that # only popped one operand.
Kind of depends on how you're using the postfix expression once it's built. If you want to display it then your special # operator would probably confuse people. But if you're just using it internally (which I was), then it works great.

Traverse through the string, and replace all unary minus operators with 0- and surround the result with parenthesis. For example, given -20 + (-2 * 50), transform it to (0-20) + ((0-2) * 50).

Related

How to build a binary expression tree from a prefix notation?

something like this ( * (+ 1 2 3) 5)
Operator like *, + can have more than two operands.
To make prefix notation with unbounded number of operands you should define some additional rules for open/close brackets (and that's not what prefix notation generaly does).
Simple parser will take operation, first operand and add other operands one by one. On each step just create new operation node, left operand will take previous (current) result, right operand will take newly fetched operand.
Continue up to the end of input or close bracket. Do not remove close bracket from input - it should be dealt with in open-close parse part, not in operation parse.
Taking operand is straightforward:
"(" -> go deeper and parse subexpression up to ")".
Different operation - > go deeper and parse sub expression.
Same operation cam be simply ignored, but it's up to you.
Constant (or variable if you have them) -> make operand subexpression.

Ruby evaluate an expression with regex, no eval

Sorry if this is duplicated. I thought I'd reword my question a little bit.
How could I use regex to evaluate a mathematical expression? Without using the eval function.
Example expressions:
math1 = "1+1"
math2 = "3+2-1"
I would like it to work for a variable number of numbers in the expression like I showed in the example.
This is just a bad idea. Regexp is not a parser, nor an evaluator.
Use a grammar to describe your expressions. Parse it with a formal parser like the lovely ruby gem Treetop. Then evaluate the abstract syntax tree (AST) produced by the parser.
Gosh, Treetop's arithmetic example practically gives you the solution for free.
This is a little late, but I wrote a gem for evaluating arbitrary mathematical expressions (and it doesn't use eval internally): https://github.com/rubysolo/dentaku
For addition and subtraction, this should work
(?:(/d+)([-+]))+(/d+)
This means:
one or more digits, followed by exactly one plus or minus
the above can be repeated as many times as required (this is a non capturing group)
and then must end with one or more digits.
Note that each individual number and sign are captured in groups 1..n
So to evaluate, you could take captures 1 and 3, applying the sign from capture 2. Then apply the sign from capture 4 (if it exists) with the previous result and the number from capture 5 (which must exist if capture 4 exists) and so on...
So to evaluate, in psuedo code:
i=1
result=capture(i)
loop while i <= (n-2) (where n is the capture count):
If capture(i+1) == "-" // is subtraction
result = result - capture(i+2)
Else // is addition
result = result + capture(i+2)
End if
i = i + 2
End while
This is only going to work for simple addition and subtraction like in the examples you provided, as it relies on left to right associativity. As others have suggested, you'll probably need to properly parse anything more complex, eg by building a tree of nodes that can then be evaluated in the correct (depth-first?) order.
This is really messy…
math2 = "12+3-4"
head, *tail = math2.scan(/(?<digits>\d+)(?<op>[\+\-\*\/])?/)
.map{|(digits,op)|
[digits.to_i,op]
}
.reverse
tail.inject(head.first){|sum,(digits,op)|
op.nil? ?
digits :
digits.send(op,sum)
}
# => 11
You should really consider a parser though.

Why does Ruby `**` operator have higher precedence than unary `-`?

This leads to the situation like:
-1 ** 0.5 #=> -1
Only parenthesis remedies it:
(-1) ** 0.5 #=> 6.123031769111886e-17+1.0i
which is less favorable then expected 1.i, but basically acceptable. Before I go to Ruby bugs to complain, I would like to know whether there is perhaps some reason for this to be so?
Many languages define their operator precedence tables by modeling after mathematics' order of operations. In math, exponentiation does have higher precedence than multiplication, and unary negation is a multiplication, after all.
From matz in a reply to "the sign of a number is omitted when squaring it":
People with mathematical background demands precedence for ** being
higher than that of unary minus. That's the reason.
Yes, ** has a higher precedence in Ruby.
Unlike some languages, - is not lex'ed as part of the number literal and is thus just (and universally) the unary - (aka -#). That is, both -x and -1 parse the unary -# as an operator applied to the result of the expression.

what does slash(/) do in prolog?

I have this code:
set_value(X,Value,[X/_|T],[X/Value|T]).
set_value(X,Value,[Y/V|T],[Y/V|NewT):- X\=Y,set_value(X,Value,T,NewT).
set_value(X,Value,[],[X/Value]).
But I cannot figure out what does / do. It looks like it pairs variables, but I'm not 100% sure. It definitely isn't division operator. Thanks.
It doesn't do anything; it's used here to construct pairs, as you already figured.
Since the / doesn't occur on the right-hand side of is or in another place where arithmetic evaluation is performed, Prolog just produces two-argument terms with / as the functor. / is used because it can be written infix; - is also a popular choice for a generic pair constructor.

Why do we need prefix, postfix notation

I know how each of them can be converted to one another but never really understood what their applications are. The usual infix operation is quite readable, but where does it fail which led to inception of prefix and postfix notation
Infix notation is easy to read for humans, whereas pre-/postfix notation is easier to parse for a machine. The big advantage in pre-/postfix notation is that there never arise any questions like operator precedence.
For example, consider the infix expression 1 # 2 $ 3. Now, we don't know what those operators mean, so there are two possible corresponding postfix expressions: 1 2 # 3 $ and 1 2 3 $ #. Without knowing the rules governing the use of these operators, the infix expression is essentially worthless.
Or, to put it in more general terms: it is possible to restore the original (parse) tree from a pre-/postfix expression without any additional knowledge, but the same isn't true for infix expressions.
Postfix notation, also known as RPN, is very easy to process left-to-right. An operand is pushed onto a stack; an operator pops its operand(s) from the stack and pushes the result. Little or no parsing is necessary. It's used by Forth and by some calculators (HP calculators are noted for using RPN).
Prefix notation is nearly as easy to process; it's used in Lisp.
At least for the case of the prefix notation: The advantage of using a prefix operator is that syntactically, it reads as if the operator is a function call
Another aspect of prefix/postfix vs. infix is that the arity of the operator (how many arguments it is applied to) no longer has to be limited to exactly 2. It can be more, or sometimes less (0 or 1 when defaults are implied naturally, like zero for addition/subtraction, one for multiplication/division).

Resources