# 1. Lua¶

Lua is a powerful and fast scripting language that is easy to learn. In UniPlot R2016 Lua can be used parallel with UniScript. UniPlot uses LuaJIT (http://www.luajit.org) from Mike Pall.

The first edition of “Programming in Lua” by Roberto Ierusalimschy, Lua.org, December 2003, ISBN 8590379817 is available online: http://www.lua.org/pil/contents.html

## 1.2. Short comparison of Lua and UniScript¶

Here is an example in UniScipt. The function finds the index of the maximum element in a vector:

 ``` 1 2 3 4 5 6 7 8 9 10 11 12 13 14``` ```// Maximum and index of a vector def maximum(a) { mi = 1; m = a[mi]; for (i in 1:len(a)) { if (a[i] > m) { mi = i; m = a[i]; } } return [m, mi]; } ```

To create the function, we use a UniPlot-Editor. The file must be saved with the extension `.ic`. The UniScript=>Save/Execute command or the function key F4 translates the function. To invoke the function, open the command window (View=>Command Window). First we create a vector with 1,000,000 random numbers in the range 0 to 1.

```* r = rand(1,1e6)
```
```* tic(); maximum(r); toc()
56.1462
```

`tic()` starts a timer and `toc()` returns the time since the timer has been started in milliseconds.

Here is the same function in Lua.

 ``` 1 2 3 4 5 6 7 8 9 10 11 12 13``` ```-- Maximum and index of a vector function maximum(a) local mi = 1 local m = a[mi] for i = 1, #a do if a[i] > m then mi = i m = a[i] end end return m, mi end ```

The function must be saved in a file with the extension `.lua`.

The first line is a comment. In Lua, comments start with a doublehyphen `--` and run until the end of the line.

Instead of `def` the Lua function is created with the `function` keyword. In UniScript statements are enclosed in braces `{ ... }`. Lua uses the end keyword.

```function ... end
for ... do ... end
if ... then ... end
```

The first statement in UniScript is `mi = 1;` and in Lua `local mi = 1`.

In UniScript all variables inside a function are local variables. To create a global variable, it must be declared at the beginning of the function using the `global` keyword.

In Lua a local variable must be declared before using it with the keyword `local`. Otherwise the variable is global. See also http://lua-users.org/wiki/LocalByDefault.

To compile the Lua function press F4 in the editor. To execute the function open the the command window. To switch into the Lua mode type in `.lua`.

Now you can execute the following statements:

 ```1 2 3 4``` ```> a = {}; for i=1,1e6 do a[i] = math.random() end > up = require"uniplot" > up.tic(); maximum(a); print(up.toc()) 0.95537533378229 ```

The first command creates a Lua table with 1 million elements. The `random()` function from the Lua `math` library will create a random number.

The second statement loads the `uniplot` library for the functions `tic()` and `toc()`. They use the Windows `QueryPerformanceCounter` function to measure the execution time.

The Lua function takes approx. one millisecond. The UniScript function takes approx. 50 milliseconds. The reasons are: 1.) LuaJIT is a Just-In-Time compiler, 2.) UniScript is an interpreter.

In practice, UniScript will call a C function to calculate the maximum. Exit the Lua command window with the `exit` command. In the UniScript command window the maxi function can be invoked. This function is even a bit faster than the Lua function.

```* a = rand(1e6,1);
* tic(); maxi(a); toc()
0.7638
```

## 1.3. UniScript Interface¶

The `r = us.call(us_func_name, p1, ...)` function is used to call an UniScript function. The interface is loaded from the `lua_uniscript.dll` dll. Example:

```us = require "lua-uniscript"   -- load lua-uniscript.dll
m = us.call("sin", 1)
print(m)
0.8414709848079
```

If a UniScript function returns a scalar number, it will be converted to a Lua number. In all other cases the UniScript value will be converted to a Lua `userdata` element.

```x = us.call("linspace", 0, 2*math.pi, 1e5)
print(x)
matrix: 0x22e70660
print(type(x))
userdata
```

`x` is a UniScript vector with 100,000 points.

```y = us.call("sin", x)
us.call("plot", x, y)
```

Normally `us.call()` will not be invoked directly. A wrapper function is used instead. Here are some examples of the `uniplot` module:

```-- uniplot.lua

local us = require "lua-uniscript"
local mat = require "uniplot.matrix"

local u = {}

u.abs = function(a1)
return mat:new(us.call("abs", a1))
end

u.acos = function(a1)
return mat:new(us.call("acos", a1))
end

u.acosh = function(a1)
return mat:new(us.call("acosh", a1))
end

return u
```

With the following two packages

```up = require"uniplot"
mat = require"uniplot.matrix"
```

the following UniScript operators can be executed:

UniScript Lua Comment
`a + b` `a + b` or `mat.add(a, b)` The matrices must have the same size or must be scalars.
`a - b` `a - b` or `mat.sub(a, b)` Subtraction.
`a * b` `a * b` or `mat.mul(a, b)` Matrix multiplication
`a .* b` `mat.emul(a, b)` Multiplication element wise
`a / b` `a / b` or `mat.div(a, b)`
`a ./ b` `mat.ediv(a, b)` Disision element wise
`a \ b`
`a'` `a:trans()` Transponse.
`a.'` `a:etrans()`
`nr(a)` `a:nr()` or `mat.nr(a)` Number of rows.
`nc(a)` `a:nc()` or `mat.nc(a)` Number of columns.
`len(a)` `#a` or `a:len()` or `mat.len(a)` Number of elements of a vector.
`a^-1` or `inv(a)` `a^-1` or `a:inv()` or `mat.inv(a)` Inverse of a matrix.
`[1,2,3]` `mat.matrix{1,2,3}` Row vector
`[1;2;3]` `mat.matrix({1,2,3}):trans()` Column vector.
`[1,2;3,4]` `up.reshape(mat.matrix{1,2,3,4}, 2, 2):trans()` Matrix
`[a, b]` `mat.hcat(a,b)` Concatenate matrices horizontally
`[a; b]` `mat.vcat(a,b)` Concatenate matrices vertical
`a < b`, `<= == != > >=` `mat.lt(a, b)`, `le, eq, ne, gt, ge` Compare operators for matrices and vectors.
`a & b, a | b, a@b, ~a, a << b, a >> b` `mat.band(a, b)`, `bor, xor, not, shl, shr` Bit wise and, or, exclusiv or, not, shift left, shift right
`1:10`, `1:0.5:3`, `3:1` `mat.range(1, 10)`, `mat.range(1,0.5,3)`, `mat.range(3, 1)` Sequence `[1, 2, .. 10]`, `[1, 1.5, 2, 2.5, 3]`, `[3, 2, 1]`
`b = a[i;j]` `b = a:rowcol(i, j)`
`a[i;]`, `a[;j]` `a:row(i)`, `a:col(j)`
`a[:]` reshape(a, 1, #a)
`c = 1+3i` `c = complex(1, 3)` Create complex numbers and matrices.

## 1.4. Lua Debugger¶

A Lua-Debugger will be available in one of the next releases.

## 1.5. Remarks¶

• The LuaJIT version is 2.1-beta, 2016-01-18 with `-DLUAJIT_ENABLE_LUA52COMPAT` enabled. The DLL `luajit.dll` is compiled using the Microsoft Visual Studio 2015 kompiliert with the C-Runtime-Library `msvcr120.dll`.

The LuaJIT DLL can be replaced by an owner build DLL.

id-1010283