# The maybe modality
```agda
module foundation.maybe where
```
<details><summary>Imports</summary>
```agda
open import foundation.coproduct-types
open import foundation.decidable-types
open import foundation.dependent-pair-types
open import foundation.equality-coproduct-types
open import foundation.type-arithmetic-empty-type
open import foundation.unit-type
open import foundation.universe-levels
open import foundation-core.embeddings
open import foundation-core.empty-types
open import foundation-core.equivalences
open import foundation-core.identity-types
open import foundation-core.injective-maps
open import foundation-core.negation
```
</details>
## Idea
The maybe modality is an operation on types that adds one point. This is used,
for example, to define partial functions, where a partial function `f : X ⇀ Y`
is a map `f : X → Maybe Y`.
## Definitions
### The Maybe modality
```agda
Maybe : {l : Level} → UU l → UU l
Maybe X = X + unit
data Maybe' {l} (X : UU l) : UU l where
unit-Maybe' : X → Maybe' X
exception-Maybe' : Maybe' X
{-# BUILTIN MAYBE Maybe' #-}
unit-Maybe : {l : Level} {X : UU l} → X → Maybe X
unit-Maybe = inl
exception-Maybe : {l : Level} {X : UU l} → Maybe X
exception-Maybe {l} {X} = inr star
```
### The predicate of being an exception
```agda
is-exception-Maybe : {l : Level} {X : UU l} → Maybe X → UU l
is-exception-Maybe {l} {X} x = (x = exception-Maybe)
is-not-exception-Maybe : {l : Level} {X : UU l} → Maybe X → UU l
is-not-exception-Maybe x = ¬ (is-exception-Maybe x)
```
### The predicate of being a value
```agda
is-value-Maybe : {l : Level} {X : UU l} → Maybe X → UU l
is-value-Maybe {l} {X} x = Σ X (λ y → inl y = x)
value-is-value-Maybe :
{l : Level} {X : UU l} (x : Maybe X) → is-value-Maybe x → X
value-is-value-Maybe x = pr1
eq-is-value-Maybe :
{l : Level} {X : UU l} (x : Maybe X) (H : is-value-Maybe x) →
inl (value-is-value-Maybe x H) = x
eq-is-value-Maybe x H = pr2 H
```
### Maybe structure on a type
```agda
maybe-structure : {l1 : Level} (X : UU l1) → UU (lsuc l1)
maybe-structure {l1} X = Σ (UU l1) (λ Y → Maybe Y ≃ X)
```
## Properties
### The unit of Maybe is an embedding
```agda
abstract
is-emb-unit-Maybe : {l : Level} {X : UU l} → is-emb (unit-Maybe {X = X})
is-emb-unit-Maybe {l} {X} = is-emb-inl X unit
emb-unit-Maybe : {l : Level} (X : UU l) → X ↪ Maybe X
pr1 (emb-unit-Maybe X) = unit-Maybe
pr2 (emb-unit-Maybe X) = is-emb-unit-Maybe
abstract
is-injective-unit-Maybe :
{l : Level} {X : UU l} → is-injective (unit-Maybe {X = X})
is-injective-unit-Maybe = is-injective-inl
```
### Being an exception is decidable
```agda
is-decidable-is-exception-Maybe :
{l : Level} {X : UU l} (x : Maybe X) → is-decidable (is-exception-Maybe x)
is-decidable-is-exception-Maybe {l} {X} (inl x) =
inr (λ p → ex-falso (is-empty-eq-coproduct-inl-inr x star p))
is-decidable-is-exception-Maybe (inr star) = inl refl
is-decidable-is-not-exception-Maybe :
{l : Level} {X : UU l} (x : Maybe X) → is-decidable (is-not-exception-Maybe x)
is-decidable-is-not-exception-Maybe x =
is-decidable-neg (is-decidable-is-exception-Maybe x)
```
### The values of the unit of the Maybe modality are not exceptions
```agda
abstract
is-not-exception-unit-Maybe :
{l : Level} {X : UU l} (x : X) → is-not-exception-Maybe (unit-Maybe x)
is-not-exception-unit-Maybe {l} {X} x ()
```
### For any element of type `Maybe X` we can decide whether it is a value or an exception
```agda
decide-Maybe :
{l : Level} {X : UU l} (x : Maybe X) → is-value-Maybe x + is-exception-Maybe x
decide-Maybe (inl x) = inl (pair x refl)
decide-Maybe (inr star) = inr refl
```
### Values are not exceptions
```agda
abstract
is-not-exception-is-value-Maybe :
{l1 : Level} {X : UU l1} (x : Maybe X) →
is-value-Maybe x → is-not-exception-Maybe x
is-not-exception-is-value-Maybe {l1} {X} .(inl x) (pair x refl) =
is-not-exception-unit-Maybe x
```
### If a point is not an exception, then it is a value
```agda
is-value-is-not-exception-Maybe :
{l1 : Level} {X : UU l1} (x : Maybe X) →
is-not-exception-Maybe x → is-value-Maybe x
is-value-is-not-exception-Maybe x H =
map-right-unit-law-coproduct-is-empty
( is-value-Maybe x)
( is-exception-Maybe x)
( H)
( decide-Maybe x)
value-is-not-exception-Maybe :
{l1 : Level} {X : UU l1} (x : Maybe X) → is-not-exception-Maybe x → X
value-is-not-exception-Maybe x H =
value-is-value-Maybe x (is-value-is-not-exception-Maybe x H)
eq-is-not-exception-Maybe :
{l1 : Level} {X : UU l1} (x : Maybe X) (H : is-not-exception-Maybe x) →
inl (value-is-not-exception-Maybe x H) = x
eq-is-not-exception-Maybe x H =
eq-is-value-Maybe x (is-value-is-not-exception-Maybe x H)
```
### The two definitions of `Maybe` are equal
```agda
equiv-Maybe-Maybe' :
{l1 l2 : Level} {X : UU l1} → Maybe X ≃ Maybe' X
pr1 equiv-Maybe-Maybe' (inl x) = unit-Maybe' x
pr1 equiv-Maybe-Maybe' (inr star) = exception-Maybe'
pr1 (pr1 (pr2 equiv-Maybe-Maybe')) (unit-Maybe' x) = inl x
pr1 (pr1 (pr2 equiv-Maybe-Maybe')) exception-Maybe' = inr star
pr2 (pr1 (pr2 equiv-Maybe-Maybe')) (unit-Maybe' x) = refl
pr2 (pr1 (pr2 equiv-Maybe-Maybe')) exception-Maybe' = refl
pr1 (pr2 (pr2 equiv-Maybe-Maybe')) (unit-Maybe' x) = inl x
pr1 (pr2 (pr2 equiv-Maybe-Maybe')) exception-Maybe' = inr star
pr2 (pr2 (pr2 equiv-Maybe-Maybe')) (inl x) = refl
pr2 (pr2 (pr2 equiv-Maybe-Maybe')) (inr star) = refl
```