## Initializing Tuples

Tuples can be created similarly to arrays, replacing square brackets with parenthesis. For example,

```
t = (3.14, 2.72)
```

Creates a variable with type `Tuple{Float64, Float64}`

, whose values can be accessed via `t[1]`

and `t[2]`

.

In fact, we don’t even need the parenthesis to initialize a tuple, and simply doing

```
t = 3.14, 2.72
```

will work just as well.

## Destructuring Tuples

We can cast the elements of a tuple as different variables in a very straightforward manner:

```
pi_approx, e_approx = t
```

Tuples are, for this reason, a convenient return type for a function that seemingly returns multiple outputs, such as we discussed in the post about functions.

## Converting Tuples to Arrays

Tuples can be converted to arrays in various ways: using the `collect`

function, array comprehensions, or the `splat`

notation.

```
a = (1, 2, 3)
t1 = collect(a);
t2 = [x for x in a];
t3 = [a...];
```

all producing the same output:

```
3-element Vector{Int64}:
1
2
3
```

## Named Tuples

An interesting variant is that we can assign names to the different elements of a tuple. For example, by declaring

```
p = ( x = 1.1, y = 2.4)
```

The elements of `p`

can be accessed via `p.x`

and `p.y`

as well as `p[1]`

and `p[2]`

.

`p`

is of type `NamedTuple{(:x, :y), Tuple{Float64, Float64}}`

.

We can also retrieve the names of the keys and the values of a named tuple, using the `keys`

and `values`

functions, as follows:

```
K = keys(p) # (:x, :y)
V = values(p) # (1.1, 2.4)
```

and we can merge this key/value pairs into a named tuple again with the `zip`

function:

```
p_new = (; zip(K,V)...) # (x = 1.1, y = 2.4)
```

Since Julia 1.7, there is a new sytnax that can be used to destructure a NamedTuple:

```
(; y, x) = p
```

This syntax is equivalent to

```
y = getproperty(p, :y);
x = getproperty(p, :x)
```

so in particular it will generate the new variables regardless of the order in which they are stored or queried.