# Preliminary#

## Vectors#

fib-o-mat ships a `Vector`

class which represent a 2-dim mathematical vector or point in euclidean space. A vector can be constructed in
various ways:

`Vector()`

creates a null-vector

`Vector(x=1, y=2) = Vector(1, 2)`

creates a cartesian vector with (1, 2) as components

`Vector(np.array([1, 2]))`

creates the same vector as above from a numpy array

`Vector([1, 2])`

creates the same vector as above from a list

`Vector((1, 2))`

creates the same vector as above from a tuple

`Vector(r=1, phi=np.pi)`

creates a vector from polar coordinates

`Vector(Vector(1, 2))`

copies the passed vector object

`Vector`

support the usual mathematical operations

```
u = Vector(1, 2)
v = Vector(3, 4)
print(u + v) # result in Vector(4, 6)
print(u - v) # result in Vector(-2, -2)
print(4 * u) # result in Vector(4, 8)
print(u / 2) # result in Vector(0.5, 1)
print(u + (1, 2)) # results also in Vector(4, 6)
print(u + [1, 2]) # results also in Vector(4, 6)
print(u + np.array((1, 2))) # results also in Vector(4, 6)
print(u.dot(v)) # prints the dot product between u and v, in this case 9
```

Vectors can be accessed component-wise

```
print(u.x, u.y) # prints "1, 2"
print(u[0], u[1]) # prints "1, 2", too. u[0] = u.x, u[1] = u.y
w = Vector(r=1, phi=np.pi)
print(u.r, u.phi) # prints 1, 3.14159
```

Warning

Vector values cannot be changed by accessing its elements. E.g. `u.x = 5`

is not working.
To change a component, a new `Vector`

must be constructed
`new_u = Vector(x=5, y=u.y)`

Further, some other properties of the vector can be accessed

```
print(v.length) # prints out the norm (length) of the vector
print(v.angle_about_x_axis) # prints the angle of the vector and the positive x-axis. the result will be in [0, 2pi]
print(u.close_to(v)) # returns True, if u is nearly v and otherwise False.
print(angle_between(u, v)) # prints the angle between u and v
```

Some other operations which can be applied to vectors

```
u_rot = u.rotated(np.pi/2) # rotated the vector counterclockwise by np.pi/2 around the origin.
u_mir = u.mirrored([1, 0]) # mirrors the vector at the positive x-axis
u_norm = u.normalized() # returns a vector pointing in the same direction as `u` but with length = 1
```

`Vector`

can be converted to a numpy array with

```
np_array = np.asarray(u)
```

To describe dimensioned vectors, the `DimVector`

class exist.
This class supports the same function and methods as given above for the `Vector`

class.

Todo

Add example here.

All the code snippets above are combined here: viggge/fib-o-mat/-/blob/master/examples/vectors.py.

Note

Not all methods on and with vectors are introduced above. Please consult the module reference for all available functions and methods.

## Physical units#

fibomat uses the pint library to represent physical units. All functionality is encapsulated in the `units`

submodule.

A unit can be constructed with

```
length_unit = U_('µm')
dose_unit = U_('ions / nm**2')
```

Quantities can be defined nearly identical

```
length = Q_('1 nm')
dose = Q_('10 ions / nm**2')
another_length = 10 * length_unit # equal to 10 * U_('µm')
# three version to create a dimensioned vector
dim_vector = (3, 4) * U_('µm')
dim_vector2 = Vector(3, 4) * U_('µm')
dim_vector3 = DimVector(3 * U_('µm'), 4 * U_('µm'))
```

Quantities can be scaled and scale factors can be calculated

```
length_in_um = scale_to(U_('µm'), length) # NOTE: length_in_um is a float now and NOT a quantity anymore
scale_factor = scale_factor(U_('µm'), U_('nm')) # scale factor (float) to scale from nm to µm
```

Alternatively, all functions and methods defined in the pint module itself can be used

```
length_in_um = length.m_as('µm') # identical to scale_to(U_('µm'), length)
# ...
```

Examples given in: viggge/fib-o-mat/-/blob/master/examples/units.py.

## Immutability#

All classes besides the `Sample`

, `Site`

and the lattice builder classes are immutable.
This means, once an object is constructed, it cannot be changed or altered anymore.

For example, the x component of `Vector`

can be read but not set or the
`rotated()`

method returns a
rotated `Vector`

but will not change the original one.