Skip to content

5.1 Operators

Claude Roux edited this page Dec 14, 2023 · 4 revisions

Operators

back

Here is an exhaustive description of the operators provided by LispE. Note that when these operators can applied to one single list, in which case, they apply this operation to all elements inside.

%: remainder of an integer division

(% 10 3) ; gives 1

*: multiplication

(* 10 2) ; gives 20

+: numerical addition or concatenation of strings

(+ 10 20) ; gives 30
(+ "test" "=" "empty") ; gives "test=empty".

-: subtraction

Be careful to put a space after the minus, otherwise the interpretation will be that of a negative number.

(- 10 2) ; gives 8

/: division

(/ 10 6) ; gives 1.66667

<<: left shift

(<< 10 1) ; gives 20

>>: right shift

(>> 10 1) ; gives 5

^^: power

(^^ 10 2) ; gives 100

**: power (an alternative to ^^)

(** 10 2) ; gives 100

&: bitwise and

(& 10 2) ; gives 2

&~: bitwise and not

(&~ 10 2) ; gives 8

|: bitwise or

(| 10 6) ; gives 14

^: bitwise xor

(^ 10 2) ; gives 8

~: bitwise not

(~ 10) ; gives -11

!: factorial of n

(! 6) ; yields 720

Operation and local modification

All operators can be used in the form: +=, *=, /= etc.

The only constraint is that the first element must be a variable.

; We create a variable:

(setq r 10)
(+= r 10)

; r is now 20

Operators on Lists

The following operators take two lists, sets or strings and apply an intersection, a union, or an exclusive union (xor). These operators then generate a new element, which contains some elements from both objects, without any duplicates.

intersection: (&&& o1 o2)

The intersection returns a list (string or set), which contains the elements that exist in both objects.

(setq r '(10 20 30 40 30 40))
(setq v '(10 2 2 60 30 4 50 60))

(&&& r v) ; (10 30)

; With sets
(setq r (seti 10 20 30 40))
(setq v (seti 10 2 30 4 50 60))

(&&& r v) ; {10 30}

; with strings
(setq r "aabbccdfedefghij")
(setq v "acaeeegik")

(&&& r v) ; acegi

union: (||| o1 o2)

The union returns a list (string or set), which contains all the elements from both objects.

(setq r '(10 20 30 40 30 40))
(setq v '(10 2 2 60 30 4 50 60))

(||| r v) ; (10 20 30 40 2 60 4 50)

; With sets
(setq r (seti 10 20 30 40))
(setq v (seti 10 2 30 4 50 60))

(||| r v) ; {2 4 10 20 30 40 50 60}

; with strings
(setq r "aabbccdfedefghij")
(setq v "acaeeegik")

(||| r v) ; abcdfeghijk

exclusive union: (^^^ o1 o2)

The exclusive union returns a list (string or set), which contains a union of both lists minus the common elements.

(setq r '(10 20 30 40 30 40))
(setq v '(10 2 2 60 30 4 50 60))

(^^^ r v) ; (20 40 2 60 4 50)

; With sets
(setq r (seti 10 20 30 40))
(setq v (seti 10 2 30 4 50 60))

(^^^ r v) ; {2 4 20 40 50 60}

; with strings
(setq r "aabbccdfedefghij")
(setq v "acaeeegik")

(^^^ r v) ; bdfhjk

Infix

The way mathematical formulas are written in LispE do not always make the expressions very readable. LispE provides a specific operator: infix that allows mathematical expressions to be written infixed. The only constraint is that operators and operands must be separated with a space.

These expressions are compiled on the fly and replaced in the code with their actual LispE interpretation. The way the expression is compiled takes into account the traditional notion of operator precedence.

It is also possible to have an idea of how these expressions are actually compiled if you put them in a lambda in the console, which is then compiled into the final expression. Furthermore, note that the infix operator only applies to the top expression in parentheses. If you have a sub-expression within the expression, you will need to use the infix operator again.

infix or /\ oror §

Each of these four operators is equivalent.

; This is compiled as (lambda (x) (- (+ 10 20) (* 4 x)))
(lambda (x) (infix 10 + 20 - 4 * x)) 

; This is compiled as (lambda (x) (- (+ (^^ x 3) (* 10 (^^ x 2)) (* 2 x)) 1))
(lambda (x) (• x ^^ 3 + 10 * x ^^ 2 + 2 * x - 1)) 

; This is compiled as (lambda (x) (- (+ (* 10 (^^ (- x 1) 2)) (* 2 (- 4 x))) 1))
; If you don't use the infix operator in an expression, you need to write it as usual
(lambda (x) (/\ 10 * (§ x - 1) ^^ 2 + 2 * (- 4 x) - 1)) 

(infix list)

If infix is provided with a list or a variable, then the transformation is applied during the execution.

(infix '(12 + 30)) ; (+ 12 30)

Operations With Lists

Note that all these operators can recursively apply between lists:

; Operation between two or more lists
(+ '(1 2 3) '(4 5 6) '(3 2 1)) ; yields (8 9 10)

; Operation with a scalar
(- '(10 9 8) 4) ; yields (6 5 4)

; Operation with a list of lists and another list
(+ '((1 2 3) (4 5 6 7) (1 1 1)) '(2 2 2)) ; yields ((3 4 5) (6 7 8 9) (3 3 3))

Comparisons

The comparison operators are as follows:

=: equal

The difference with eq is that eq does not recursively compare lists or dictionaries, while = does.

(= 10 10) ; yields true
(= '(1 2 3) '(1 2 3)) ; yields true

!=: different

(!= 10 20) ; yields true
(!= '(1 2 R) '(1 2 A)) ; yields true

<: less

(< 10 100) ;gives true

<= : less or equal

(<= 10 10) ;gives true

>: more

(> 10 5) ; gives true

>=: greater or equal

(>= 10 10) ; gives true

>=<: GEL operator (>=< x y)

The GEL operator (g is pronounced as in get) is mainly used with heaps.

  • It returns -1 is x is lower than y.
  • It returns 0 is x is equal to y.
  • It returns 1 is x is greater than y.
(>=< 10 10) ; yields 0
(>=< 10 11) ; yields -1
(>=< 11 10) ; yields 1
Clone this wiki locally