*This article, which is the first part of the mathematical journey through open source, takes you through the basic mathematics through a shell.*

Mathematics is something which is knowingly or unknowingly part of every moment of our life, starting from the interpretation of the moment – the time to shopping to advanced engineering calculations and computations. We have learnt mathematics from our childhood by counting. With the age of computers, we have been taught how to do mathematics with them. In this journey of mathematics, we are going to tour through the various open source softwares with their mathematical capabilities. Today, we start with the most preliminary one the shell.

**Shell command ‘expr’**

*expr* supports the basic arithmetic operations: Addition (+), Subtraction (-), Multiplication (\*), Quotient (/), Remainder (%) – with the C-like precedence & associativity rules. So, if that’s what you want, you may use it as follows:

```
$ expr 2 + 3
5
$ expr 34 – 67
-33
$ expr 23 \* 27
621
$ expr 43 / 6
7
$ expr 43 % 6
1
$ expr 2 + 2 \* 3 – 5 + 21 / 4 \* 6
33
```

Note the spaces between every one of the *expr*, numbers, and the operator – *expr* is very space-sensitive. The power of this simple command is its precision-less-ness. What I mean is, try out the following:

`$ expr 1024 \* 1024 \* 1024 \* 1024 \* 1024 \* 1024 \* 1024 \* 1024 \* 1024 \* 1024`

And you still don’t get an overflow, but 1267650600228229401496703205376, i.e. 2^{100}.

Also, you may use variables. Here’s an example:

```
$ x=5; y=6; z=`expr $x + $y`
$ echo $z
11
```

However, it has its own limitation. Basic one being, you do not have the exponentiation operator. Moreover, you can’t change precedences by using brackets. And that’s where you start looking at the other options.

**Shell’s arithmetic expansion**

With this, we get the all the mathematical C operators, plus the exponentiation using **. We have the bracketing, and variable usage even without the cryptic $. It is achieved by putting the complete expression to be evaluated, between *$((…))* – the arithmetic expander. Here’s a set of examples:

```
$ echo $(((2+3)*4-2**4/5%6))
17
$ x=y=8; echo $((3 << 4 | x | 2 << y))
568
```

There are some additional interesting ways to assign variables, as well, using *let* or *declare -i*.

```
$ let x=y=8 z='3 << 4 | x | 2 << y' w=z/3
$ echo $w
189
$ declare -i x=y=8 z='3 << 4 | x | 2 << y' w=z/3
$ echo $w
189
```

Note that the *$((…))* has been replaced by single quoting in assigning the value to z. In fact, in most cases – see the assignment of w – it can be actually assigned directly as in C. Though the single quote for z is required to prevent the shell specially interpreting constructs like *<<, >>, |, **, etc, and for it not to be space-sensitive. Otherwise, checkout, this example:

```
$ declare -i x=y=8 z=++x+y
$ echo $z
17
```

In fact, the variables can be declared as integer once, and then be operated any number of times, as follows:

```
$ declare -i x y z
$ x=y=8
$ z=++x+y
$ echo $z
17
```

And, finally here’s two simple ones:

$ echo $((2 ** 100)) 0 $ echo $((2.6 + 3)) bash: 2.6 + 3: syntax error: invalid arithmetic operator (error token is ".6 + 3")

Oops!!! how come 2^{100} is zero, and we are not able to do real number operations. It has its own limitation. It is limited by the C’s *long integer* math, typically upto 64-bit computations on today’s computers; and by not having support for non-integer math. That’s where we would look out for something more powerful: the bench calculator.

Vivek SrimathiI tried to evaluate this on the shell

expr 1024 * 1024 * 1024 * 1024 * 1024 * 1024 * 1024 * 1024 * 1024 * 1024

I got the message as follows:

expr: *: Numerical result out of range

But your shell doesn’t seem to have this problem. How?

Im using bash. what shell are you using?

Anil PugaliaPlease post the output of the following commands:

$ expr –version

$ which expr

$ ldd /bin/expr

Vivek Srimathi$ expr –version

expr (GNU coreutils) 8.5

Copyright (C) 2010 Free Software Foundation, Inc.

License GPLv3+: GNU GPL version 3 or later .

This is free software: you are free to change and redistribute it.

There is NO WARRANTY, to the extent permitted by law.

Written by Mike Parker, James Youngman, and Paul Eggert.

$which expr

/usr/bin/expr

$ldd /bin/expr

ldd: /bin/expr: No such file or directory

I tried the following

$ldd /usr/bin/expr

linux-gate.so.1 => (0x00e29000)

libc.so.6 => /lib/i386-linux-gnu/libc.so.6 (0x00209000)

/lib/ld-linux.so.2 (0x006c9000)

Anil PugaliaHmmm! expr on your system is not using the GNU Multi Precision library as it is not compiled with the gmp library. Instead it is using the normal C math operations, limited by the max integer & real number sizes limited by C. And hence the difference.

On my system, ldd /usr/bin/expr shows the following: (See the additional libgmp.so.10)

linux-gate.so.1 => (0xffffe000)

libgmp.so.10 => /usr/lib/libgmp.so.10 (0xb7671000)

libc.so.6 => /lib/i686/libc.so.6 (0xb751f000)

/lib/ld-linux.so.2 (0xb76ff000)