5.7 Generalizations of inductive types

5.7 Generalizations of inductive types

The notion of inductive type has been studied in

type theory

for many years, and admits of many, many

generalizations

: inductive type families, mutual inductive types, inductive-inductive types, inductive-recursive types, etc.
In this

section

we give an overview of some of these, a few of which will be used later in the book.
(In

http://planetmath.org/node/87579

Chapter 6 we will study in more depth a very different generalization of inductive types, which is particular to

homotopy

type theory.)

Most of these generalizations involve allowing ourselves to define more than one type by

induction

at the same time.
One very simple example of this, which we have already seen, is the

coproduct

A

+

B

.
It would be tedious indeed if we had to write down separate inductive definitions for

ℕ

+

ℕ

, for

ℕ

+

𝟐

, for

𝟐

+

𝟐

, and so on every time we wanted to consider the coproduct of two types.
Instead, we make one

definition

in which

A

and

B

are

variables

standing for types;
in type theory they are called

parameters

.
Thus technically speaking, what results from the definition is not a single type, but a family of types

+

:

𝒰

→

𝒰

→

𝒰

, taking two types as input and producing their coproduct.
Similarly, the type

𝖫𝗂𝗌𝗍

⁢

(

A

)

of lists is a family

𝖫𝗂𝗌𝗍

⁢

(

¯

)

:

𝒰

→

𝒰

in which the type

A

is a parameter.

In mathematics, this sort of thing is so

obvious

as to not be worth mentioning, but we bring it up in order to contrast it with the next example.
Note that each type

A

+

B

is

independently

defined inductively, as is each type

𝖫𝗂𝗌𝗍

⁢

(

A

)

.
By contrast, we might also consider defining a whole type family

B

:

A

→

𝒰

by induction

together

.
The

difference

is that now the constructors may change the index

a

:

A

, and as a

consequence

we cannot say that the

individual

types

B

⁢

(

a

)

are inductively defined, only that the entire family is inductively defined.

The standard example is the type of

lists of specified length

, traditionally called

vectors

.
We fix a parameter type

A

, and define a type family

𝖵𝖾𝖼

n

⁢

(

A

)

, for

n

:

ℕ

, generated by the following constructors:

•

a vector

𝗇𝗂𝗅

:

𝖵𝖾𝖼

0

⁢

(

A

)

of length zero,

•

a

function

𝖼𝗈𝗇𝗌

:

∏

(

n

:

ℕ

)

A

→

𝖵𝖾𝖼

n

⁢

(

A

)

→

𝖵𝖾𝖼

𝗌𝗎𝖼𝖼

⁢

(

n

)

⁢

(

A

)

.

In contrast to lists, vectors (with

elements

from a fixed type

A

) form a family of types

indexed by

their length.
While

A

is a parameter, we say that

n

:

ℕ

is an

index

of the inductive family.
An individual type such as

𝖵𝖾𝖼

3

⁢

(

A

)

is not inductively defined: the constructors which build elements of

𝖵𝖾𝖼

3

⁢

(

A

)

take input from a different type in the family, such as

𝖼𝗈𝗇𝗌

:

A

→

𝖵𝖾𝖼

2

⁢

(

A

)

→

𝖵𝖾𝖼

3

⁢

(

A

)

.

In particular, the induction principle must refer to the entire type family as well; thus the hypotheses and the

conclusion

must quantify over the indices appropriately.
In the case of vectors, the induction principle states that given a type family

C

:

∏

(

n

:

ℕ

)

𝖵𝖾𝖼

n

⁢

(

A

)

→

𝒰

, together with

•

an element

c

𝗇𝗂𝗅

:

C

⁢

(

0

,

𝗇𝗂𝗅

)

, and

•

a function

c

𝖼𝗈𝗇𝗌

:

∏

(

n

:

ℕ

)

∏

(

a

:

A

)

∏

(

ℓ

:

𝖵𝖾𝖼

n

(

A

)

)

C

⁢

(

n

,

ℓ

)

→

C

⁢

(

𝗌𝗎𝖼𝖼

⁢

(

n

)

,

𝖼𝗈𝗇𝗌

⁢

(

a

,

ℓ

)

)

there exists a function

f

:

∏

(

n

:

ℕ

)

∏

(

ℓ

:

𝖵𝖾𝖼

n

(

A

)

)

C

⁢

(

n

,

ℓ

)

such that

f

⁢

(

0

,

𝗇𝗂𝗅

)

≡

c

𝗇𝗂𝗅

f

⁢

(

𝗌𝗎𝖼𝖼

⁢

(

n

)

,

𝖼𝗈𝗇𝗌

⁢

(

a

,

ℓ

)

)

≡

c

𝖼𝗈𝗇𝗌

⁢

(

n

,

a

,

ℓ

,

f

⁢

(

ℓ

)

)

.

One use of inductive families is to define

predicates

inductively.
For

instance

, we might define the predicate

𝗂𝗌𝖾𝗏𝖾𝗇

:

ℕ

→

𝒰

as an inductive family indexed by

ℕ

, with the following constructors:

•

an element

𝖾𝗏𝖾𝗇

0

:

𝗂𝗌𝖾𝗏𝖾𝗇

⁢

(

0

)

,

•

a function

𝖾𝗏𝖾𝗇

s

⁢

s

:

∏

(

n

:

ℕ

)

𝗂𝗌𝖾𝗏𝖾𝗇

⁢

(

n

)

→

𝗂𝗌𝖾𝗏𝖾𝗇

⁢

(

𝗌𝗎𝖼𝖼

⁢

(

𝗌𝗎𝖼𝖼

⁢

(

n

)

)

)

.

In other words, we stipulate that

0

is even, and that if

n

is even then so is

𝗌𝗎𝖼𝖼

⁢

(

𝗌𝗎𝖼𝖼

⁢

(

n

)

)

.
These constructors “obviously” give no way to

construct

an element of, say,

𝗂𝗌𝖾𝗏𝖾𝗇

⁢

(

1

)

, and since

𝗂𝗌𝖾𝗏𝖾𝗇

is supposed to be

freely generated

by these constructors, there must be no such element.
(Actually proving that

¬

⁢

𝗂𝗌𝖾𝗏𝖾𝗇

⁢

(

1

)

is not entirely

trivial

, however).
The induction principle for

𝗂𝗌𝖾𝗏𝖾𝗇

says that to prove something about all even

natural numbers

, it suffices to prove it for

0

and verify that it is preserved by adding two.

Inductively defined predicates are much used in

computer

formalization of mathematics and software verification.
But we will not have much use for them, with a couple of exceptions in §10.3 (

http://planetmath.org/103ordinalnumbers

),§11.5 (

http://planetmath.org/115compactnessoftheinterval

).

Another important special case is when the indexing type of an inductive family is finite.
In this case, we can equivalently express the inductive definition as a finite

collection

of types defined by

mutual induction

.
For instance, we might define the types

𝖾𝗏𝖾𝗇

and

𝗈𝖽𝖽

of even and odd natural numbers by mutual induction, where

𝖾𝗏𝖾𝗇

is generated by constructors

•

0

:

𝖾𝗏𝖾𝗇

and

•

𝖾𝗌𝗎𝖼𝖼

:

𝗈𝖽𝖽

→

𝖾𝗏𝖾𝗇

,

while

𝗈𝖽𝖽

is generated by the one constructor

•

𝗈𝗌𝗎𝖼𝖼

:

𝖾𝗏𝖾𝗇

→

𝗈𝖽𝖽

.

Note that

𝖾𝗏𝖾𝗇

and

𝗈𝖽𝖽

are simple types (not type families), but their constructors can refer to each other.
If we expressed this definition as an inductive type family

𝗉𝖺𝗋𝗂𝗍𝗒𝗇𝖺𝗍

:

𝟐

→

𝒰

, with

𝗉𝖺𝗋𝗂𝗍𝗒𝗇𝖺𝗍

⁢

(

0

𝟐

)

and

𝗉𝖺𝗋𝗂𝗍𝗒𝗇𝖺𝗍

⁢

(

1

𝟐

)

representing

𝖾𝗏𝖾𝗇

and

𝗈𝖽𝖽

respectively, it would instead have constructors:

•

0

:

𝗉𝖺𝗋𝗂𝗍𝗒𝗇𝖺𝗍

⁢

(

0

𝟐

)

,

•

𝖾𝗌𝗎𝖼𝖼

:

𝗉𝖺𝗋𝗂𝗍𝗒𝗇𝖺𝗍

⁢

(

0

𝟐

)

→

𝗉𝖺𝗋𝗂𝗍𝗒𝗇𝖺𝗍

⁢

(

1

𝟐

)

,

•

𝗈𝖾𝗌𝗎𝖼𝖼

:

𝗉𝖺𝗋𝗂𝗍𝗒𝗇𝖺𝗍

⁢

(

1

𝟐

)

→

𝗉𝖺𝗋𝗂𝗍𝗒𝗇𝖺𝗍

⁢

(

0

𝟐

)

.

When expressed explicitly as a mutual inductive definition, the induction principle for

𝖾𝗏𝖾𝗇

and

𝗈𝖽𝖽

says that given

C

:

𝖾𝗏𝖾𝗇

→

𝒰

and

D

:

𝗈𝖽𝖽

→

𝒰

, along with

•

c

0

:

C

⁢

(

0

)

,

•

c

s

:

∏

(

n

:

𝗈𝖽𝖽

)

D

⁢

(

n

)

→

C

⁢

(

𝖾𝗌𝗎𝖼𝖼

⁢

(

n

)

)

,

•

d

s

:

∏

(

n

:

𝖾𝗏𝖾𝗇

)

C

⁢

(

n

)

→

D

⁢

(

𝗈𝗌𝗎𝖼𝖼

⁢

(

n

)

)

,

there exist

f

:

∏

(

n

:

𝖾𝗏𝖾𝗇

)

C

⁢

(

n

)

and

g

:

∏

(

n

:

𝗈𝖽𝖽

)

D

⁢

(

n

)

such that

f

⁢

(

0

)

≡

c

0

f

⁢

(

𝖾𝗌𝗎𝖼𝖼

⁢

(

n

)

)

≡

c

s

⁢

(

g

⁢

(

n

)

)

g

⁢

(

𝗈𝗌𝗎𝖼𝖼

⁢

(

n

)

)

≡

d

s

⁢

(

f

⁢

(

n

)

)

.

In particular, just as we can only induct over an inductive family “all at once”, we have to induct on

𝖾𝗏𝖾𝗇

and

𝗈𝖽𝖽

simultaneously.
We will not have much use for mutual inductive definitions in this book either.

A further, more

radical

, generalization is to allow definition of a type family

B

:

A

→

𝒰

in which not only the types

B

⁢

(

a

)

, but the type

A

itself, is defined as part of one big induction.
In other words, not only do we specify constructors for the

B

⁢

(

a

)

s which can take inputs from other

B

⁢

(

a

′

)

s, as with inductive families, we also at the same time specify constructors for

A

itself, which can take inputs from the

B

⁢

(

a

)

s.
This can be regarded as an inductive family in which the indices are inductively defined simultaneously with the indexed types, or as a mutual inductive definition in which one of the types can depend on the other.
More complicated dependency

structures

are also possible.
In general, these are called

inductive-inductive definitions

.
For the most part, we will not use them in this book, but their higher variant (see

http://planetmath.org/node/87579

Chapter 6) will appear in a couple of experimental examples in

http://planetmath.org/node/87585

Chapter 11.

The last generalization we wish to mention is

inductive-recursive definitions

, in which a type is defined inductively at the same time as a

recursive

function on it.
That is, we fix a known type

P

, and give constructors for an inductive type

A

and at the same time define a function

f

:

A

→

P

using the

recursion

principle for

A

resulting from its constructors — with the twist that the constructors of

A

are allowed to refer also to the values of

f

.
We do not yet know how to justify such definitions from a homotopical perspective, and we will not use any of them in this book.

Title

5.7 Generalizations of inductive types

\metatable

Generated on Thu Feb 8 19:37:01 2018 by

LaTeXML