Common operator notation

Last updated

In programming languages, scientific calculators and similar common operator notation or operator grammar is a way to define and analyse mathematical and other formal expressions. In this model a linear sequence of tokens are divided into two classes: operators and operands.

Contents

Operands are objects upon which the operators operate. These include literal numbers and other constants as well as identifiers (names) which may represent anything from simple scalar variables to complex aggregated structures and objects, depending on the complexity and capability of the language at hand as well as usage context. One special type of operand is the parenthesis group. An expression enclosed in parentheses is typically recursively evaluated to be treated as a single operand on the next evaluation level.

Each operator is given a position, precedence, and an associativity. The operator precedence is a number (from high to low or vice versa) that defines which operator takes an operand that is surrounded by two operators of different precedence (or priority). Multiplication normally has higher precedence than addition, [1] for example, so 3+4×5 = 3+(4×5) ≠ (3+4)×5.

In terms of operator position, an operator may be prefix, postfix, or infix. A prefix operator immediately precedes its operand, as in −x. A postfix operator immediately succeeds its operand, as in x! for instance. An infix operator is positioned in between a left and a right operand, as in x+y. Some languages, most notably the C-syntax family, stretches this conventional terminology and speaks also of ternary infix operators (a?b:c). Theoretically it would even be possible (but not necessarily practical) to define parenthesization as a unary bifix operation.

Operator associativity

Operator associativity determines what happens when an operand is surrounded by operators of the same precedence, as in 1-2-3: An operator can be left-associative, right-associative, or non-associative. Left-associative operators are applied to operands in left-to-right order while right-associative operators are the other way round. The basic arithmetic operators are normally all left-associative, [1] which means that 1-2-3 = (1-2)-3 ≠ 1-(2-3), for instance. This does not hold true for higher operators. For example, exponentiation is normally right-associative in mathematics, [1] but is implemented as left-associative in some computer applications like Excel. In programming languages where assignment is implemented as an operator, that operator is often right-associative. If so, a statement like a := b := c would be equivalent to a := (b := c), which means that the value of c is copied to b which is then copied to a. An operator which is non-associative cannot compete for operands with operators of equal precedence. In Prolog for example, the infix operator :- is non-associative, so constructs such as a :- b :- c are syntax errors. Unary prefix operators such as − (negation) or sin (trigonometric function) are typically associative prefix operators. When more than one associative prefix or postfix operator of equal precedence precedes or succeeds an operand, the operators closest to the operand goes first. So −sin x = −(sin x), and sin -x = sin(-x).

Mathematically oriented languages (such as on scientific calculators) sometimes allow implicit multiplication with higher priority than prefix operators (such as sin), so that sin 2x+1 = (sin(2x))+1, for instance.[ citation needed ]

However, prefix (and postfix) operators do not necessarily have higher precedence than all infix operators. Some (hypothetical) programming language may well have an operator called sin with a precedence lower than × but higher than + for instance. In such a language, sin 2·x+1 = sin(2·x)+1 would be true, instead of (sin 2)·x+1, as would normally be the case.

The rules for expression evaluation are usually three-fold:

  1. Treat any sub-expression in parentheses as a single recursively-evaluated operand (there may be different kinds of parentheses though, with different semantics).
  2. Bind operands to operators of higher precedence before those of lower precedence.
  3. For equal precedence, bind operands to operators according to the associativity of the operators.

Some more examples:

1-2+3/4*5+6+7 = (((1-2)+((3/4)*5))+6)+7
4 + -x + 3 = (4 + (-x)) + 3

Generalizations of Common Operator Notation

The use of operator precedence classes and associativities is just one way. However, it is not the most general way: this model cannot give an operator more precedence when competing with '−' than it can when competing with '+', while still giving '+' and '−' equivalent precedences and associativities. A generalized version of this model (in which each operator can be given independent left and right precedences) can be found at .

See also

Related Research Articles

<span class="mw-page-title-main">Logical connective</span> Symbol connecting sentential formulas in logic

In logic, a logical connective is a logical constant. They can be used to connect logical formulas. For instance in the syntax of propositional logic, the binary connective can be used to join the two atomic formulas and , rendering the complex formula .

In mathematics, an operand is the object of a mathematical operation, i.e., it is the object or quantity that is operated on.

In computer programming, operator overloading, sometimes termed operator ad hoc polymorphism, is a specific case of polymorphism, where different operators have different implementations depending on their arguments. Operator overloading is generally defined by a programming language, a programmer, or both.

Polish notation (PN), also known as normal Polish notation (NPN), Łukasiewicz notation, Warsaw notation, Polish prefix notation or simply prefix notation, is a mathematical notation in which operators precede their operands, in contrast to the more common infix notation, in which operators are placed between operands, as well as reverse Polish notation (RPN), in which operators follow their operands. It does not need any parentheses as long as each operator has a fixed number of operands. The description "Polish" refers to the nationality of logician Jan Łukasiewicz, who invented Polish notation in 1924.

Rebol is a cross-platform data exchange language and a multi-paradigm dynamic programming language designed by Carl Sassenrath for network communications and distributed computing. It introduces the concept of dialecting: small, optimized, domain-specific languages for code and data, which is also the most notable property of the language according to its designer Carl Sassenrath:

Although it can be used for programming, writing functions, and performing processes, its greatest strength is the ability to easily create domain-specific languages or dialects

In mathematics, a unary operation is an operation with only one operand, i.e. a single input. This is in contrast to binary operations, which use two operands. An example is any function f : AA, where A is a set. The function f is a unary operation on A.

<span class="mw-page-title-main">Infix notation</span> Mathematics notation with operators between operands

Infix notation is the notation commonly used in arithmetical and logical formulae and statements. It is characterized by the placement of operators between operands—"infixed operators"—such as the plus sign in 2 + 2.

In mathematics and computer programming, the order of operations is a collection of rules that reflect conventions about which procedures to perform first in order to evaluate a given mathematical expression.

In programming language theory, the associativity of an operator is a property that determines how operators of the same precedence are grouped in the absence of parentheses. If an operand is both preceded and followed by operators, and those operators have equal precedence, then the operand may be used as input to two different operations. The choice of which operations to apply the operand to, is determined by the associativity of the operators. Operators may be associative, left-associative, right-associative or non-associative. The associativity and precedence of an operator is a part of the definition of the programming language; different programming languages may have different associativity and precedence for the same type of operator.

This is a list of operators in the C and C++ programming languages. All the operators listed exist in C++; the column "Included in C", states whether an operator is also present in C. Note that C does not support operator overloading.

In computer programming, the ternary conditional operator is a ternary operator that is part of the syntax for basic conditional expressions in several programming languages. It is commonly referred to as the conditional operator, ternary if, or inline if. An expression a ? b : c evaluates to b if the value of a is true, and otherwise to c. One can read it aloud as "if a then b otherwise c". The form a ? b : c is by far and large the most common, but alternative syntaxes do exist; for example, Raku uses the syntax a ?? b !! c to avoid confusion with the infix operators ? and !, whereas in Visual Basic .NET, it instead takes the form If(a, b, c).

In computer programming, operators are constructs defined within programming languages which behave generally like functions, but which differ syntactically or semantically.

Stack-oriented programming is a programming paradigm which relies on a stack machine model for passing parameters. Stack-oriented languages operate on one or more stacks, each of which may serve a different purpose. Programming constructs in other programming languages need to be modified for use in a stack-oriented system. Most stack-oriented languages operate in postfix or Reverse Polish notation. Any arguments or parameters for a command are stated before that command. For example, postfix notation would be written 2, 3, multiply instead of multiply, 2, 3, or 2 multiply 3. The programming languages Forth, Factor, RPL, PostScript, BibTeX style design language and many assembly languages fit this paradigm.

In computer science, an operator precedence parser is a bottom-up parser that interprets an operator-precedence grammar. For example, most calculators use operator precedence parsers to convert from the human-readable infix notation relying on order of operations to a format that is optimized for evaluation such as Reverse Polish notation (RPN).

There are various ways in which calculators interpret keystrokes. These can be categorized into two main types:

In computer science, the shunting yard algorithm is a method for parsing arithmetical or logical expressions, or a combination of both, specified in infix notation. It can produce either a postfix notation string, also known as Reverse Polish notation (RPN), or an abstract syntax tree (AST). The algorithm was invented by Edsger Dijkstra and named the "shunting yard" algorithm because its operation resembles that of a railroad shunting yard. Dijkstra first described the shunting yard algorithm in the Mathematisch Centrum report MR 34/61.

In computer science, a Boolean expression is an expression used in programming languages that produces a Boolean value when evaluated. A Boolean value is either true or false. A Boolean expression may be composed of a combination of the Boolean constants true or false, Boolean-typed variables, Boolean-valued operators, and Boolean-valued functions.

In the C and C++ programming languages, the comma operator is a binary operator that evaluates its first operand and discards the result, and then evaluates the second operand and returns this value ; there is a sequence point between these evaluations.

<span class="mw-page-title-main">Formula calculator</span>

A formula calculator is a software calculator that can perform a calculation in two steps:

  1. Enter the calculation by typing it in from the keyboard.
  2. Press a single button or key to see the final result.

Increment and decrement operators are unary operators that increase or decrease their operand by one.

References

  1. 1 2 3 Bronstein, Ilja Nikolaevič; Semendjajew, Konstantin Adolfovič (1987) [1945]. "2.4.1.1.". In Grosche, Günter; Ziegler, Viktor; Ziegler, Dorothea (eds.). Taschenbuch der Mathematik (in German). Vol. 1. Translated by Ziegler, Viktor. Weiß, Jürgen (23 ed.). Thun and Frankfurt am Main: Verlag Harri Deutsch (and B. G. Teubner Verlagsgesellschaft, Leipzig). pp. 115–120. ISBN   3-87144-492-8.