# Science tools borrow Rust

## Hi! I'm Hanneli

• Computer Engineer
• Programming
• Electronics
• Math <3 <3
• Physics
• Lego
• Meetups
• Animals
• Coffee
• GIFs

# DISCLAIMER

### Some slides contain code drafts (do not try to run them)

Architecture opinions are on my own

## Agenda

• About trending tools in science
• Octave, Data Analysis and Machine Learning
• Linear Algebra intro
• Rust and basic Matrices discussion
• Functions involving complex numbers and Rust
• Lessons learned on types, safety and Rust Language

Machine Learning

Big Data

Data Analysis

# I was talking to some students about these topics

"We use some tools to help us with math"

# Tools - Octave

### I was talking to some students about these topics

Do you like it?

Yes, but it is hard to express math with C or C++

### I was talking to some students about these topics

Have you tried Rust?

No, what is Rust?

### I was talking to some students about these topics

I think I can _borrow_ you some knowledge

Is it safe?

# (Thanks)

## Agenda

• About trending tools in science
• Octave, Data Analysis and Machine Learning
• Linear Algebra intro
• Rust and basic Matrices discussion
• Functions involving complex numbers and Rust
• Lessons learned on types, safety and Rust Language

Octave is very useful for Machine Learning and Data analysis

Normalising the data

Operations with Matrices

Plotting charts

Statistics

# Octave is Open Source

Open Source <3

## Agenda

• About trending tools in science √
• Octave, Data Analysis and Machine Learning
• Linear Algebra intro
• Rust and basic Matrices discussion
• Functions involving complex numbers and Rust
• Lessons learned on types, safety and Rust Language

# Octave external packages

## Agenda

• About trending tools in science √
• Octave, Data Analysis and Machine Learning√
• Linear Algebra intro
• Rust and basic Matrices discussion
• Functions involving complex numbers and Rust
• Lessons learned on types, safety and Rust Language

# Do you remember high school times? Physics lectures:

Electronic circuits and Ohm's Law (U = R x I)

Va

R4

R5

Vb

R1

R2

R3

# The circuits can be more sophisticated:

Va

R4

R5

Vb

R1

R2

R3

V1

V2

i1

i2

i4

i2

i3

i5

### We can describe the system with some equations:

i1 - i2 - i4 = 0

i2 - i3 - i5 = 0

1/R1 (Va-V1) - 1/R2 (V1-V2) - 1/R4 (V1) = 0
$1/R1 (Va-V1) - 1/R2 (V1-V2) - 1/R4 (V1) = 0$
1/R2 (V1-V2) - 1/R3 (V2-Vb) - 1/R5 (V2) = 0
$1/R2 (V1-V2) - 1/R3 (V2-Vb) - 1/R5 (V2) = 0$

{

{

# There is a different way to represent these systems

1/R1 (Va-V1) - 1/R2 (V1-V2) - 1/R4 (V1) = 0
$1/R1 (Va-V1) - 1/R2 (V1-V2) - 1/R4 (V1) = 0$
1/R2 (V1-V2) - 1/R3 (V2-Vb) - 1/R5 (V2) = 0
$1/R2 (V1-V2) - 1/R3 (V2-Vb) - 1/R5 (V2) = 0$

{

Expanding the system (lots of Algebraic work):

1/R1 (Va-V1) - 1/R2 (V1-V2) - 1/R4 (V1) = 0
$1/R1 (Va-V1) - 1/R2 (V1-V2) - 1/R4 (V1) = 0$
1/R2 (V1-V2) - 1/R3 (V2-Vb) - 1/R5 (V2) = 0
$1/R2 (V1-V2) - 1/R3 (V2-Vb) - 1/R5 (V2) = 0$

{

Expanding the system (lots of Algebraic work):

(1/R1 + 1/R2 + 1/R4)V1 - 1/R2(V2) = (Va/R1)
$(1/R1 + 1/R2 + 1/R4)V1 - 1/R2(V2) = (Va/R1)$
(-1/R2)V1 + (1/R2 + 1/R3 + 1/R5)V2 = (Vb/R3)
$(-1/R2)V1 + (1/R2 + 1/R3 + 1/R5)V2 = (Vb/R3)$

{

# Understanting and resolving such systems is a big topic in Linear Algebra

## Agenda

• About trending tools in science√
• Octave, Data Analysis and Machine Learning√
• Linear Algebra intro√
• Rust and basic Matrices discussion
• Functions involving complex numbers and Rust
• Lessons learned on types, safety and Rust Language

# We have matrices in Octave:

template <class T>
Array<T>::Array (int n, const T& val)
{
//code
}

template <class T>
Array<T>&
Array<T>::operator = (const Array<T>& a)
{
if (this != &a && rep != a.rep)
{
if (--rep->count <= 0)
delete rep;

rep = a.rep;
rep->count++;
}

// code

return *this;
}

// more code

# Building a simple matrix in Rust

pub struct Matrix<T> {
rows: usize,
cols: usize,
elements: Vec<T>,
}

# There is a rule to multiply matrices

[

3   5   8

1   1  9

]

x

[

7   9   1   0

5   3   7   9

1   1   0   4

]

Rows: 2

Cols: 3

Rows: 3

Cols: 4

[

3   5   8

1   1  9

]

x

[

7   9   1   0

5   3   7   9

1   1   0   4

]

Rows: 2

Cols: 3

Rows: 3

Cols: 4

pub struct Matrix<T> {
rows: 2,
cols: 3,
elements: Vec<T>,
}
pub struct Matrix<T> {
rows: 3,
cols: 4,
elements: Vec<T>,
}

Explicit Matrix1.cols == Matrix2.rows

pub struct Matrix<T> {
rows: usize,
cols: usize,
elements: Vec<T>,
}
pub trait Dimension {

// we have a behaviour set
// for Dimensions
}
impl Dimension for Matrix {

}

# We can also describe the matrix elements in terms of a type:

impl<E, D> Matrix<E, D>
where E: PhantomData,
D: Dimension
{
// better
}
*PhantomData: "PhantomData<T> allows you to describe that a type acts as if it stores a value of type T, even though it does not."

https://doc.rust-lang.org/std/marker/struct.PhantomData.html
Inspiration: http://jadpole.github.io/rust/typechecked-matrix

# Extra: Can you think of a code to represent square matrices?

[

3   5

1   1

]

Rows == Cols == 2

## Agenda

• About trending tools in science√
• Octave, Data Analysis and Machine Learning√
• Linear Algebra intro√
• Rust and basic Matrices discussion√
• Functions involving complex numbers and Rust
• Lessons learned on types, safety and Rust Language

# Off topic moment of this lecture:

Integer

+

Integer

=

Integer

1

+

1

=

2

Adding integers will always result in another integer.

This is not true for division

Integer

/

Integer

=

May not be an Integer

# ALL TEH NUMBERZ! (?)

Real

/

Real

=

Real

Real

-

Real

=

Real

Real

x

Real

=

Real

Real

+

Real

=

Real

Is there any operation within real numbers that does not result in a real number?

# Yes

√Real

=

May not be Real

√-4

=

Not a Real number

Complex Numbers are important because they output complex numbers for all the common algebraic operations

# Let's try with Rust

pub struct ComplexNumber<T> {
real: T,
imaginary: T,
}

# ->ComplexNumber<T>

pub fn pow(&self, exp: T) -> ComplexNumber<T> {
// stay inside the Complex number set
}

Why is this important?

### You can create a trait with this idea

trait ClosedSet

# Note: Complex<T> is included in num[*]

[*] https://github.com/rust-num/num

## Agenda

• About trending tools in science√
• Octave, Data Analysis and Machine Learning√
• Linear Algebra intro√
• Rust and basic Matrices discussion√
• Functions involving complex numbers and Rust√
• Lessons learned on types, safety and Rust Language

## Lessons Learned

• There are great tools to help us with science and engineering, but sometimes the existing code is verbose.
• Or it is sad to handle with dangling pointers and memory allocation problems.
• It is also non trivial how to express the types
• Converting from mathematics to code is not always trivial.
• Rust can be helpful to resolve most of these points.
• Rust compiler can help to prevent runtime errors (clients of traits are fully-typed checked).

### Rust compiler can help to prevent runtime errors

Imagine running a long script in Octave and get a runtime error after several minutes of processing: it can be frustrating.

We can delegate this code to Rust.

# Last, bust not least:

These concepts or mindset can be applied to other areas, not only scientific projects.

Example: wouldn't the idea of closed sets be useful for payments?

The idea of creating a trait for specific abstractions, like the Matrix Dimension, could be good as well.

# unsafe

pub unsafe fn from_vector(d: Dimension, v: Vec<A>) -> Matrix<T>
{
// at some point calls slice::get_unchecked
}

# NOOOOO

## It is okay to have an unsafe constructor, but wrap it into a safe structure.

fn from_safe_vec_impl(d: Dimension, v: Vec<A>)
-> Result<Matrix<T>, ConversionError>
{
if d.size_checked() != Some(v.len()) {
return
Err(error::incompatible_shapes(&v.len(),
&dim));
}
unsafe { Ok(Self::from_vector(dim, v)) }
}
}

# mut (when you were not supposed to use it)

Fast Fourier Transform (FFT)

fn from_time(s: &mut Signal<Time>) -> Signal<Frequency>

fn from_frequency(s: &mut Signal<Frequency>) -> Signal<Time>

# Once you have a measurement, it is immutable by definition! This code does not make sense!

Fast Fourier Transform (FFT)

fn from_time(s: Signal<Time>) -> Signal<Frequency>

fn from_frequency(s: Signal<Frequency>) -> Signal<Time>

(this is more appropriate!)

# References

• https://github.com/servo/euclid
• https://github.com/bluss/rust-ndarray
• https://athemathmo.github.io/2016/03/23/linear-algebra-in-rust.html
• https://github.com/rust-num/num
• https://doc.rust-lang.org/reference.html
• http://pnkfelix.github.io/curry-on2015.html#/
• http://rustbyexample.com/
• ftp://ftp.cs.washington.edu/tr/2015/03/UW-CSE-15-03-02.pdf
• https://killercup.github.io/trpl-ebook/nomicon-2016-06-02.a4.pdf
• https://blog.rust-lang.org/2015/05/11/traits.html

## Special Thanks

• Daniel Hahn, for being a great mentor
• B.C., for the constant review
• @lafp, @romulostorel       and @pedrofelipee      (GIFs)
• rust_br community :)

## Thank you :)

Questions?

hannelita@gmail.com

@hannelita

#### RustFest

By Hanneli Tavante (hannelita)

• 2,130